blob: 60375d11614cef40c051300ca7a26e39ba955b92 [file] [log] [blame]
Bram Moolenaardb913952012-06-29 12:54:53 +02001/* vi:set ts=8 sts=4 sw=4 noet:
Bram Moolenaar170bf1a2010-07-24 23:51:45 +02002 *
3 * VIM - Vi IMproved by Bram Moolenaar
4 *
5 * Do ":help uganda" in Vim to read copying and usage conditions.
6 * Do ":help credits" in Vim to see a list of people who contributed.
7 * See README.txt for an overview of the Vim source code.
8 */
9/*
10 * Python extensions by Paul Moore, David Leonard, Roland Puntaier.
11 *
12 * Common code for if_python.c and if_python3.c.
13 */
14
Bram Moolenaarc1a995d2012-08-08 16:05:07 +020015#if PY_VERSION_HEX < 0x02050000
16typedef int Py_ssize_t; /* Python 2.4 and earlier don't have this type. */
17#endif
18
Bram Moolenaar91805fc2011-06-26 04:01:44 +020019#ifdef FEAT_MBYTE
20# define ENC_OPT p_enc
21#else
22# define ENC_OPT "latin1"
23#endif
24
Bram Moolenaar170bf1a2010-07-24 23:51:45 +020025/*
26 * obtain a lock on the Vim data structures
27 */
28 static void
29Python_Lock_Vim(void)
30{
31}
32
33/*
34 * release a lock on the Vim data structures
35 */
36 static void
37Python_Release_Vim(void)
38{
39}
40
41/* Output object definition
42 */
43
44static PyObject *OutputWrite(PyObject *, PyObject *);
45static PyObject *OutputWritelines(PyObject *, PyObject *);
Bram Moolenaara29a37d2011-03-22 15:47:44 +010046static PyObject *OutputFlush(PyObject *, PyObject *);
Bram Moolenaar170bf1a2010-07-24 23:51:45 +020047
Bram Moolenaar2eea1982010-09-21 16:49:37 +020048/* Function to write a line, points to either msg() or emsg(). */
Bram Moolenaar170bf1a2010-07-24 23:51:45 +020049typedef void (*writefn)(char_u *);
50static void writer(writefn fn, char_u *str, PyInt n);
51
52typedef struct
53{
54 PyObject_HEAD
55 long softspace;
56 long error;
57} OutputObject;
58
59static struct PyMethodDef OutputMethods[] = {
60 /* name, function, calling, documentation */
Bram Moolenaara29a37d2011-03-22 15:47:44 +010061 {"write", OutputWrite, 1, ""},
62 {"writelines", OutputWritelines, 1, ""},
Bram Moolenaar2afa3232012-06-29 16:28:28 +020063 {"flush", OutputFlush, 1, ""},
Bram Moolenaara29a37d2011-03-22 15:47:44 +010064 { NULL, NULL, 0, NULL}
Bram Moolenaar170bf1a2010-07-24 23:51:45 +020065};
66
Bram Moolenaarca8a4df2010-07-31 19:54:14 +020067#define PyErr_SetVim(str) PyErr_SetString(VimError, str)
68
Bram Moolenaar170bf1a2010-07-24 23:51:45 +020069/*************/
70
71/* Output buffer management
72 */
73
74 static PyObject *
75OutputWrite(PyObject *self, PyObject *args)
76{
77 int len;
Bram Moolenaar19e60942011-06-19 00:27:51 +020078 char *str = NULL;
Bram Moolenaar170bf1a2010-07-24 23:51:45 +020079 int error = ((OutputObject *)(self))->error;
80
Bram Moolenaar27564802011-09-07 19:30:21 +020081 if (!PyArg_ParseTuple(args, "et#", ENC_OPT, &str, &len))
Bram Moolenaar170bf1a2010-07-24 23:51:45 +020082 return NULL;
83
Bram Moolenaarb830f0c2012-04-20 13:31:21 +020084 /* TODO: This works around a gcc optimizer problem and avoids Vim
85 * from crashing. Should find a real solution. */
86 if (str == NULL)
87 return NULL;
88
Bram Moolenaar170bf1a2010-07-24 23:51:45 +020089 Py_BEGIN_ALLOW_THREADS
90 Python_Lock_Vim();
91 writer((writefn)(error ? emsg : msg), (char_u *)str, len);
92 Python_Release_Vim();
93 Py_END_ALLOW_THREADS
Bram Moolenaar19e60942011-06-19 00:27:51 +020094 PyMem_Free(str);
Bram Moolenaar170bf1a2010-07-24 23:51:45 +020095
96 Py_INCREF(Py_None);
97 return Py_None;
98}
99
100 static PyObject *
101OutputWritelines(PyObject *self, PyObject *args)
102{
103 PyInt n;
104 PyInt i;
105 PyObject *list;
106 int error = ((OutputObject *)(self))->error;
107
108 if (!PyArg_ParseTuple(args, "O", &list))
109 return NULL;
110 Py_INCREF(list);
111
Bram Moolenaardb913952012-06-29 12:54:53 +0200112 if (!PyList_Check(list))
113 {
Bram Moolenaar170bf1a2010-07-24 23:51:45 +0200114 PyErr_SetString(PyExc_TypeError, _("writelines() requires list of strings"));
115 Py_DECREF(list);
116 return NULL;
117 }
118
119 n = PyList_Size(list);
120
121 for (i = 0; i < n; ++i)
122 {
123 PyObject *line = PyList_GetItem(list, i);
Bram Moolenaar19e60942011-06-19 00:27:51 +0200124 char *str = NULL;
Bram Moolenaar170bf1a2010-07-24 23:51:45 +0200125 PyInt len;
126
Bram Moolenaardb913952012-06-29 12:54:53 +0200127 if (!PyArg_Parse(line, "et#", ENC_OPT, &str, &len))
128 {
Bram Moolenaar170bf1a2010-07-24 23:51:45 +0200129 PyErr_SetString(PyExc_TypeError, _("writelines() requires list of strings"));
130 Py_DECREF(list);
131 return NULL;
132 }
133
134 Py_BEGIN_ALLOW_THREADS
135 Python_Lock_Vim();
136 writer((writefn)(error ? emsg : msg), (char_u *)str, len);
137 Python_Release_Vim();
138 Py_END_ALLOW_THREADS
Bram Moolenaar19e60942011-06-19 00:27:51 +0200139 PyMem_Free(str);
Bram Moolenaar170bf1a2010-07-24 23:51:45 +0200140 }
141
142 Py_DECREF(list);
143 Py_INCREF(Py_None);
144 return Py_None;
145}
146
Bram Moolenaara29a37d2011-03-22 15:47:44 +0100147 static PyObject *
148OutputFlush(PyObject *self UNUSED, PyObject *args UNUSED)
149{
150 /* do nothing */
151 Py_INCREF(Py_None);
152 return Py_None;
153}
154
155
Bram Moolenaar2eea1982010-09-21 16:49:37 +0200156/* Buffer IO, we write one whole line at a time. */
157static garray_T io_ga = {0, 0, 1, 80, NULL};
Bram Moolenaar170bf1a2010-07-24 23:51:45 +0200158static writefn old_fn = NULL;
159
160 static void
Bram Moolenaar170bf1a2010-07-24 23:51:45 +0200161PythonIO_Flush(void)
162{
Bram Moolenaar2eea1982010-09-21 16:49:37 +0200163 if (old_fn != NULL && io_ga.ga_len > 0)
Bram Moolenaar170bf1a2010-07-24 23:51:45 +0200164 {
Bram Moolenaar2eea1982010-09-21 16:49:37 +0200165 ((char_u *)io_ga.ga_data)[io_ga.ga_len] = NUL;
166 old_fn((char_u *)io_ga.ga_data);
Bram Moolenaar170bf1a2010-07-24 23:51:45 +0200167 }
Bram Moolenaar2eea1982010-09-21 16:49:37 +0200168 io_ga.ga_len = 0;
Bram Moolenaar170bf1a2010-07-24 23:51:45 +0200169}
170
171 static void
172writer(writefn fn, char_u *str, PyInt n)
173{
174 char_u *ptr;
175
Bram Moolenaar2eea1982010-09-21 16:49:37 +0200176 /* Flush when switching output function. */
177 if (fn != old_fn)
Bram Moolenaar170bf1a2010-07-24 23:51:45 +0200178 PythonIO_Flush();
Bram Moolenaar170bf1a2010-07-24 23:51:45 +0200179 old_fn = fn;
180
Bram Moolenaar2eea1982010-09-21 16:49:37 +0200181 /* Write each NL separated line. Text after the last NL is kept for
182 * writing later. */
Bram Moolenaar170bf1a2010-07-24 23:51:45 +0200183 while (n > 0 && (ptr = memchr(str, '\n', n)) != NULL)
184 {
185 PyInt len = ptr - str;
186
Bram Moolenaar6b5ef062010-10-27 12:18:00 +0200187 if (ga_grow(&io_ga, (int)(len + 1)) == FAIL)
Bram Moolenaar2eea1982010-09-21 16:49:37 +0200188 break;
Bram Moolenaar170bf1a2010-07-24 23:51:45 +0200189
Bram Moolenaar2eea1982010-09-21 16:49:37 +0200190 mch_memmove(((char *)io_ga.ga_data) + io_ga.ga_len, str, (size_t)len);
191 ((char *)io_ga.ga_data)[io_ga.ga_len + len] = NUL;
192 fn((char_u *)io_ga.ga_data);
Bram Moolenaar170bf1a2010-07-24 23:51:45 +0200193 str = ptr + 1;
194 n -= len + 1;
Bram Moolenaar2eea1982010-09-21 16:49:37 +0200195 io_ga.ga_len = 0;
Bram Moolenaar170bf1a2010-07-24 23:51:45 +0200196 }
197
Bram Moolenaar2eea1982010-09-21 16:49:37 +0200198 /* Put the remaining text into io_ga for later printing. */
Bram Moolenaar6b5ef062010-10-27 12:18:00 +0200199 if (n > 0 && ga_grow(&io_ga, (int)(n + 1)) == OK)
Bram Moolenaar2eea1982010-09-21 16:49:37 +0200200 {
201 mch_memmove(((char *)io_ga.ga_data) + io_ga.ga_len, str, (size_t)n);
Bram Moolenaar6b5ef062010-10-27 12:18:00 +0200202 io_ga.ga_len += (int)n;
Bram Moolenaar2eea1982010-09-21 16:49:37 +0200203 }
Bram Moolenaar170bf1a2010-07-24 23:51:45 +0200204}
205
206/***************/
207
208static PyTypeObject OutputType;
209
210static OutputObject Output =
211{
212 PyObject_HEAD_INIT(&OutputType)
213 0,
214 0
215};
216
217static OutputObject Error =
218{
219 PyObject_HEAD_INIT(&OutputType)
220 0,
221 1
222};
223
224 static int
225PythonIO_Init_io(void)
226{
227 PySys_SetObject("stdout", (PyObject *)(void *)&Output);
228 PySys_SetObject("stderr", (PyObject *)(void *)&Error);
229
230 if (PyErr_Occurred())
231 {
232 EMSG(_("E264: Python: Error initialising I/O objects"));
233 return -1;
234 }
235
236 return 0;
237}
238
239
240static PyObject *VimError;
241
242/* Check to see whether a Vim error has been reported, or a keyboard
243 * interrupt has been detected.
244 */
245 static int
246VimErrorCheck(void)
247{
248 if (got_int)
249 {
250 PyErr_SetNone(PyExc_KeyboardInterrupt);
251 return 1;
252 }
253 else if (did_emsg && !PyErr_Occurred())
254 {
255 PyErr_SetNone(VimError);
256 return 1;
257 }
258
259 return 0;
260}
Bram Moolenaarca8a4df2010-07-31 19:54:14 +0200261
262/* Vim module - Implementation
263 */
264 static PyObject *
265VimCommand(PyObject *self UNUSED, PyObject *args)
266{
267 char *cmd;
268 PyObject *result;
269
270 if (!PyArg_ParseTuple(args, "s", &cmd))
271 return NULL;
272
273 PyErr_Clear();
274
275 Py_BEGIN_ALLOW_THREADS
276 Python_Lock_Vim();
277
278 do_cmdline_cmd((char_u *)cmd);
279 update_screen(VALID);
280
281 Python_Release_Vim();
282 Py_END_ALLOW_THREADS
283
284 if (VimErrorCheck())
285 result = NULL;
286 else
287 result = Py_None;
288
289 Py_XINCREF(result);
290 return result;
291}
292
293#ifdef FEAT_EVAL
294/*
295 * Function to translate a typval_T into a PyObject; this will recursively
296 * translate lists/dictionaries into their Python equivalents.
297 *
298 * The depth parameter is to avoid infinite recursion, set it to 1 when
299 * you call VimToPython.
300 */
301 static PyObject *
302VimToPython(typval_T *our_tv, int depth, PyObject *lookupDict)
303{
304 PyObject *result;
305 PyObject *newObj;
Bram Moolenaardb913952012-06-29 12:54:53 +0200306 char ptrBuf[sizeof(void *) * 2 + 3];
Bram Moolenaarca8a4df2010-07-31 19:54:14 +0200307
308 /* Avoid infinite recursion */
309 if (depth > 100)
310 {
311 Py_INCREF(Py_None);
312 result = Py_None;
313 return result;
314 }
315
316 /* Check if we run into a recursive loop. The item must be in lookupDict
317 * then and we can use it again. */
318 if ((our_tv->v_type == VAR_LIST && our_tv->vval.v_list != NULL)
319 || (our_tv->v_type == VAR_DICT && our_tv->vval.v_dict != NULL))
320 {
Bram Moolenaardb913952012-06-29 12:54:53 +0200321 sprintf(ptrBuf, "%p",
322 our_tv->v_type == VAR_LIST ? (void *)our_tv->vval.v_list
323 : (void *)our_tv->vval.v_dict);
Bram Moolenaarca8a4df2010-07-31 19:54:14 +0200324 result = PyDict_GetItemString(lookupDict, ptrBuf);
325 if (result != NULL)
326 {
327 Py_INCREF(result);
328 return result;
329 }
330 }
331
332 if (our_tv->v_type == VAR_STRING)
333 {
334 result = Py_BuildValue("s", our_tv->vval.v_string);
335 }
336 else if (our_tv->v_type == VAR_NUMBER)
337 {
338 char buf[NUMBUFLEN];
339
340 /* For backwards compatibility numbers are stored as strings. */
341 sprintf(buf, "%ld", (long)our_tv->vval.v_number);
342 result = Py_BuildValue("s", buf);
343 }
344# ifdef FEAT_FLOAT
345 else if (our_tv->v_type == VAR_FLOAT)
346 {
347 char buf[NUMBUFLEN];
348
349 sprintf(buf, "%f", our_tv->vval.v_float);
350 result = Py_BuildValue("s", buf);
351 }
352# endif
353 else if (our_tv->v_type == VAR_LIST)
354 {
355 list_T *list = our_tv->vval.v_list;
356 listitem_T *curr;
357
358 result = PyList_New(0);
359
360 if (list != NULL)
361 {
362 PyDict_SetItemString(lookupDict, ptrBuf, result);
363
364 for (curr = list->lv_first; curr != NULL; curr = curr->li_next)
365 {
366 newObj = VimToPython(&curr->li_tv, depth + 1, lookupDict);
367 PyList_Append(result, newObj);
368 Py_DECREF(newObj);
369 }
370 }
371 }
372 else if (our_tv->v_type == VAR_DICT)
373 {
374 result = PyDict_New();
375
376 if (our_tv->vval.v_dict != NULL)
377 {
378 hashtab_T *ht = &our_tv->vval.v_dict->dv_hashtab;
379 long_u todo = ht->ht_used;
380 hashitem_T *hi;
381 dictitem_T *di;
382
383 PyDict_SetItemString(lookupDict, ptrBuf, result);
384
385 for (hi = ht->ht_array; todo > 0; ++hi)
386 {
387 if (!HASHITEM_EMPTY(hi))
388 {
389 --todo;
390
391 di = dict_lookup(hi);
392 newObj = VimToPython(&di->di_tv, depth + 1, lookupDict);
393 PyDict_SetItemString(result, (char *)hi->hi_key, newObj);
394 Py_DECREF(newObj);
395 }
396 }
397 }
398 }
399 else
400 {
401 Py_INCREF(Py_None);
402 result = Py_None;
403 }
404
405 return result;
406}
407#endif
408
409 static PyObject *
Bram Moolenaar09092152010-08-08 16:38:42 +0200410VimEval(PyObject *self UNUSED, PyObject *args UNUSED)
Bram Moolenaarca8a4df2010-07-31 19:54:14 +0200411{
412#ifdef FEAT_EVAL
413 char *expr;
414 typval_T *our_tv;
415 PyObject *result;
416 PyObject *lookup_dict;
417
418 if (!PyArg_ParseTuple(args, "s", &expr))
419 return NULL;
420
421 Py_BEGIN_ALLOW_THREADS
422 Python_Lock_Vim();
423 our_tv = eval_expr((char_u *)expr, NULL);
424
425 Python_Release_Vim();
426 Py_END_ALLOW_THREADS
427
428 if (our_tv == NULL)
429 {
430 PyErr_SetVim(_("invalid expression"));
431 return NULL;
432 }
433
434 /* Convert the Vim type into a Python type. Create a dictionary that's
435 * used to check for recursive loops. */
436 lookup_dict = PyDict_New();
437 result = VimToPython(our_tv, 1, lookup_dict);
438 Py_DECREF(lookup_dict);
439
440
441 Py_BEGIN_ALLOW_THREADS
442 Python_Lock_Vim();
443 free_tv(our_tv);
444 Python_Release_Vim();
445 Py_END_ALLOW_THREADS
446
447 return result;
448#else
449 PyErr_SetVim(_("expressions disabled at compile time"));
450 return NULL;
451#endif
452}
453
Bram Moolenaardb913952012-06-29 12:54:53 +0200454static PyObject *ConvertToPyObject(typval_T *);
455
456 static PyObject *
457VimEvalPy(PyObject *self UNUSED, PyObject *args UNUSED)
458{
459#ifdef FEAT_EVAL
460 char *expr;
461 typval_T *our_tv;
462 PyObject *result;
463
464 if (!PyArg_ParseTuple(args, "s", &expr))
465 return NULL;
466
467 Py_BEGIN_ALLOW_THREADS
468 Python_Lock_Vim();
469 our_tv = eval_expr((char_u *)expr, NULL);
470
471 Python_Release_Vim();
472 Py_END_ALLOW_THREADS
473
474 if (our_tv == NULL)
475 {
476 PyErr_SetVim(_("invalid expression"));
477 return NULL;
478 }
479
480 result = ConvertToPyObject(our_tv);
481 Py_BEGIN_ALLOW_THREADS
482 Python_Lock_Vim();
483 free_tv(our_tv);
484 Python_Release_Vim();
485 Py_END_ALLOW_THREADS
486
487 return result;
488#else
489 PyErr_SetVim(_("expressions disabled at compile time"));
490 return NULL;
491#endif
492}
493
494 static PyObject *
495VimStrwidth(PyObject *self UNUSED, PyObject *args)
496{
497 char *expr;
498
499 if (!PyArg_ParseTuple(args, "s", &expr))
500 return NULL;
501
Bram Moolenaar3cd3e7a2012-06-29 17:52:02 +0200502 return PyLong_FromLong(mb_string2cells((char_u *)expr, (int)STRLEN(expr)));
Bram Moolenaardb913952012-06-29 12:54:53 +0200503}
504
Bram Moolenaarca8a4df2010-07-31 19:54:14 +0200505/*
506 * Vim module - Definitions
507 */
508
509static struct PyMethodDef VimMethods[] = {
510 /* name, function, calling, documentation */
511 {"command", VimCommand, 1, "Execute a Vim ex-mode command" },
512 {"eval", VimEval, 1, "Evaluate an expression using Vim evaluator" },
Bram Moolenaar2afa3232012-06-29 16:28:28 +0200513 {"bindeval", VimEvalPy, 1, "Like eval(), but returns objects attached to vim ones"},
514 {"strwidth", VimStrwidth, 1, "Screen string width, counts <Tab> as having width 1"},
Bram Moolenaarca8a4df2010-07-31 19:54:14 +0200515 { NULL, NULL, 0, NULL }
516};
517
518typedef struct
519{
520 PyObject_HEAD
521 buf_T *buf;
Bram Moolenaardb913952012-06-29 12:54:53 +0200522} BufferObject;
Bram Moolenaarca8a4df2010-07-31 19:54:14 +0200523
524#define INVALID_BUFFER_VALUE ((buf_T *)(-1))
525
526/*
527 * Buffer list object - Implementation
528 */
529
530 static PyInt
531BufListLength(PyObject *self UNUSED)
532{
533 buf_T *b = firstbuf;
534 PyInt n = 0;
535
536 while (b)
537 {
538 ++n;
539 b = b->b_next;
540 }
541
542 return n;
543}
544
545 static PyObject *
546BufListItem(PyObject *self UNUSED, PyInt n)
547{
548 buf_T *b;
549
550 for (b = firstbuf; b; b = b->b_next, --n)
551 {
552 if (n == 0)
553 return BufferNew(b);
554 }
555
556 PyErr_SetString(PyExc_IndexError, _("no such buffer"));
557 return NULL;
558}
559
560typedef struct
561{
562 PyObject_HEAD
563 win_T *win;
564} WindowObject;
565
Bram Moolenaardb913952012-06-29 12:54:53 +0200566static int ConvertFromPyObject(PyObject *, typval_T *);
567static int _ConvertFromPyObject(PyObject *, typval_T *, PyObject *);
568
569typedef struct pylinkedlist_S {
570 struct pylinkedlist_S *pll_next;
571 struct pylinkedlist_S *pll_prev;
572 PyObject *pll_obj;
573} pylinkedlist_T;
574
575static pylinkedlist_T *lastdict = NULL;
576static pylinkedlist_T *lastlist = NULL;
577
578 static void
579pyll_remove(pylinkedlist_T *ref, pylinkedlist_T **last)
580{
581 if (ref->pll_prev == NULL)
582 {
583 if (ref->pll_next == NULL)
584 {
585 *last = NULL;
586 return;
587 }
588 }
589 else
590 ref->pll_prev->pll_next = ref->pll_next;
591
592 if (ref->pll_next == NULL)
593 *last = ref->pll_prev;
594 else
595 ref->pll_next->pll_prev = ref->pll_prev;
596}
597
598 static void
599pyll_add(PyObject *self, pylinkedlist_T *ref, pylinkedlist_T **last)
600{
601 if (*last == NULL)
602 ref->pll_prev = NULL;
603 else
604 {
605 (*last)->pll_next = ref;
606 ref->pll_prev = *last;
607 }
608 ref->pll_next = NULL;
609 ref->pll_obj = self;
610 *last = ref;
611}
612
613static PyTypeObject DictionaryType;
614
615typedef struct
616{
617 PyObject_HEAD
618 dict_T *dict;
619 pylinkedlist_T ref;
620} DictionaryObject;
621
622 static PyObject *
623DictionaryNew(dict_T *dict)
624{
625 DictionaryObject *self;
626
627 self = PyObject_NEW(DictionaryObject, &DictionaryType);
628 if (self == NULL)
629 return NULL;
630 self->dict = dict;
631 ++dict->dv_refcount;
632
633 pyll_add((PyObject *)(self), &self->ref, &lastdict);
634
635 return (PyObject *)(self);
636}
637
638 static int
639pydict_to_tv(PyObject *obj, typval_T *tv, PyObject *lookupDict)
640{
641 dict_T *d;
642 char_u *key;
643 dictitem_T *di;
644 PyObject *keyObject;
645 PyObject *valObject;
646 Py_ssize_t iter = 0;
647
648 d = dict_alloc();
649 if (d == NULL)
650 {
651 PyErr_NoMemory();
652 return -1;
653 }
654
655 tv->v_type = VAR_DICT;
656 tv->vval.v_dict = d;
657
658 while (PyDict_Next(obj, &iter, &keyObject, &valObject))
659 {
660 DICTKEY_DECL
661
662 if (keyObject == NULL)
663 return -1;
664 if (valObject == NULL)
665 return -1;
666
667 DICTKEY_GET(-1)
668
669 di = dictitem_alloc(key);
670
671 DICTKEY_UNREF
672
673 if (di == NULL)
674 {
675 PyErr_NoMemory();
676 return -1;
677 }
678 di->di_tv.v_lock = 0;
679
680 if (_ConvertFromPyObject(valObject, &di->di_tv, lookupDict) == -1)
681 {
682 vim_free(di);
683 return -1;
684 }
685 if (dict_add(d, di) == FAIL)
686 {
687 vim_free(di);
688 PyErr_SetVim(_("failed to add key to dictionary"));
689 return -1;
690 }
691 }
692 return 0;
693}
694
695 static int
696pymap_to_tv(PyObject *obj, typval_T *tv, PyObject *lookupDict)
697{
698 dict_T *d;
699 char_u *key;
700 dictitem_T *di;
701 PyObject *list;
702 PyObject *litem;
703 PyObject *keyObject;
704 PyObject *valObject;
705 Py_ssize_t lsize;
706
707 d = dict_alloc();
708 if (d == NULL)
709 {
710 PyErr_NoMemory();
711 return -1;
712 }
713
714 tv->v_type = VAR_DICT;
715 tv->vval.v_dict = d;
716
717 list = PyMapping_Items(obj);
718 lsize = PyList_Size(list);
719 while (lsize--)
720 {
721 DICTKEY_DECL
722
723 litem = PyList_GetItem(list, lsize);
724 if (litem == NULL)
725 {
726 Py_DECREF(list);
727 return -1;
728 }
729
730 keyObject = PyTuple_GetItem(litem, 0);
731 if (keyObject == NULL)
732 {
733 Py_DECREF(list);
734 Py_DECREF(litem);
735 return -1;
736 }
737
738 DICTKEY_GET(-1)
739
740 valObject = PyTuple_GetItem(litem, 1);
741 if (valObject == NULL)
742 {
743 Py_DECREF(list);
744 Py_DECREF(litem);
745 return -1;
746 }
747
748 di = dictitem_alloc(key);
749
750 DICTKEY_UNREF
751
752 if (di == NULL)
753 {
754 Py_DECREF(list);
755 Py_DECREF(litem);
756 PyErr_NoMemory();
757 return -1;
758 }
759 di->di_tv.v_lock = 0;
760
761 if (_ConvertFromPyObject(valObject, &di->di_tv, lookupDict) == -1)
762 {
763 vim_free(di);
764 Py_DECREF(list);
765 Py_DECREF(litem);
766 return -1;
767 }
768 if (dict_add(d, di) == FAIL)
769 {
770 vim_free(di);
771 Py_DECREF(list);
772 Py_DECREF(litem);
773 PyErr_SetVim(_("failed to add key to dictionary"));
774 return -1;
775 }
776 Py_DECREF(litem);
777 }
778 Py_DECREF(list);
779 return 0;
780}
781
782 static PyInt
783DictionaryLength(PyObject *self)
784{
785 return ((PyInt) ((((DictionaryObject *)(self))->dict->dv_hashtab.ht_used)));
786}
787
788 static PyObject *
789DictionaryItem(PyObject *self, PyObject *keyObject)
790{
791 char_u *key;
792 dictitem_T *val;
793 DICTKEY_DECL
794
795 DICTKEY_GET(NULL)
796
797 val = dict_find(((DictionaryObject *) (self))->dict, key, -1);
798
799 DICTKEY_UNREF
800
801 return ConvertToPyObject(&val->di_tv);
802}
803
804 static PyInt
805DictionaryAssItem(PyObject *self, PyObject *keyObject, PyObject *valObject)
806{
807 char_u *key;
808 typval_T tv;
809 dict_T *d = ((DictionaryObject *)(self))->dict;
810 dictitem_T *di;
811 DICTKEY_DECL
812
813 if (d->dv_lock)
814 {
815 PyErr_SetVim(_("dict is locked"));
816 return -1;
817 }
818
819 DICTKEY_GET(-1)
820
821 di = dict_find(d, key, -1);
822
823 if (valObject == NULL)
824 {
Bram Moolenaarf27839c2012-06-29 16:19:50 +0200825 hashitem_T *hi;
826
Bram Moolenaardb913952012-06-29 12:54:53 +0200827 if (di == NULL)
828 {
829 PyErr_SetString(PyExc_IndexError, _("no such key in dictionary"));
830 return -1;
831 }
Bram Moolenaarf27839c2012-06-29 16:19:50 +0200832 hi = hash_find(&d->dv_hashtab, di->di_key);
Bram Moolenaardb913952012-06-29 12:54:53 +0200833 hash_remove(&d->dv_hashtab, hi);
834 dictitem_free(di);
835 return 0;
836 }
837
838 if (ConvertFromPyObject(valObject, &tv) == -1)
Bram Moolenaardb913952012-06-29 12:54:53 +0200839 return -1;
Bram Moolenaardb913952012-06-29 12:54:53 +0200840
841 if (di == NULL)
842 {
843 di = dictitem_alloc(key);
844 if (di == NULL)
845 {
846 PyErr_NoMemory();
847 return -1;
848 }
849 di->di_tv.v_lock = 0;
850
851 if (dict_add(d, di) == FAIL)
852 {
853 vim_free(di);
854 PyErr_SetVim(_("failed to add key to dictionary"));
855 return -1;
856 }
857 }
858 else
859 clear_tv(&di->di_tv);
860
861 DICTKEY_UNREF
862
863 copy_tv(&tv, &di->di_tv);
864 return 0;
865}
866
867 static PyObject *
868DictionaryListKeys(PyObject *self)
869{
870 dict_T *dict = ((DictionaryObject *)(self))->dict;
871 long_u todo = dict->dv_hashtab.ht_used;
872 Py_ssize_t i = 0;
873 PyObject *r;
874 hashitem_T *hi;
875
876 r = PyList_New(todo);
877 for (hi = dict->dv_hashtab.ht_array; todo > 0; ++hi)
878 {
879 if (!HASHITEM_EMPTY(hi))
880 {
881 PyList_SetItem(r, i, PyBytes_FromString((char *)(hi->hi_key)));
882 --todo;
883 ++i;
884 }
885 }
886 return r;
887}
888
889static struct PyMethodDef DictionaryMethods[] = {
890 {"keys", (PyCFunction)DictionaryListKeys, METH_NOARGS, ""},
891 { NULL, NULL, 0, NULL }
892};
893
894static PyTypeObject ListType;
895
896typedef struct
897{
898 PyObject_HEAD
899 list_T *list;
900 pylinkedlist_T ref;
901} ListObject;
902
903 static PyObject *
904ListNew(list_T *list)
905{
906 ListObject *self;
907
908 self = PyObject_NEW(ListObject, &ListType);
909 if (self == NULL)
910 return NULL;
911 self->list = list;
912 ++list->lv_refcount;
913
914 pyll_add((PyObject *)(self), &self->ref, &lastlist);
915
916 return (PyObject *)(self);
917}
918
919 static int
920list_py_concat(list_T *l, PyObject *obj, PyObject *lookupDict)
921{
922 Py_ssize_t i;
923 Py_ssize_t lsize = PySequence_Size(obj);
924 PyObject *litem;
925 listitem_T *li;
926
927 for(i=0; i<lsize; i++)
928 {
929 li = listitem_alloc();
930 if (li == NULL)
931 {
932 PyErr_NoMemory();
933 return -1;
934 }
935 li->li_tv.v_lock = 0;
936
937 litem = PySequence_GetItem(obj, i);
938 if (litem == NULL)
939 return -1;
940 if (_ConvertFromPyObject(litem, &li->li_tv, lookupDict) == -1)
941 return -1;
942
943 list_append(l, li);
944 }
945 return 0;
946}
947
948 static int
949pyseq_to_tv(PyObject *obj, typval_T *tv, PyObject *lookupDict)
950{
951 list_T *l;
952
953 l = list_alloc();
954 if (l == NULL)
955 {
956 PyErr_NoMemory();
957 return -1;
958 }
959
960 tv->v_type = VAR_LIST;
961 tv->vval.v_list = l;
962
963 if (list_py_concat(l, obj, lookupDict) == -1)
964 return -1;
965
966 return 0;
967}
968
969 static int
970pyiter_to_tv(PyObject *obj, typval_T *tv, PyObject *lookupDict)
971{
972 PyObject *iterator = PyObject_GetIter(obj);
973 PyObject *item;
974 list_T *l;
975 listitem_T *li;
976
977 l = list_alloc();
978
979 if (l == NULL)
980 {
981 PyErr_NoMemory();
982 return -1;
983 }
984
985 tv->vval.v_list = l;
986 tv->v_type = VAR_LIST;
987
988
989 if (iterator == NULL)
990 return -1;
991
992 while ((item = PyIter_Next(obj)))
993 {
994 li = listitem_alloc();
995 if (li == NULL)
996 {
997 PyErr_NoMemory();
998 return -1;
999 }
1000 li->li_tv.v_lock = 0;
1001
1002 if (_ConvertFromPyObject(item, &li->li_tv, lookupDict) == -1)
1003 return -1;
1004
1005 list_append(l, li);
1006
1007 Py_DECREF(item);
1008 }
1009
1010 Py_DECREF(iterator);
1011 return 0;
1012}
1013
1014 static PyInt
1015ListLength(PyObject *self)
1016{
1017 return ((PyInt) (((ListObject *) (self))->list->lv_len));
1018}
1019
1020 static PyObject *
1021ListItem(PyObject *self, Py_ssize_t index)
1022{
1023 listitem_T *li;
1024
1025 if (index>=ListLength(self))
1026 {
1027 PyErr_SetString(PyExc_IndexError, "list index out of range");
1028 return NULL;
1029 }
1030 li = list_find(((ListObject *) (self))->list, (long) index);
1031 if (li == NULL)
1032 {
1033 PyErr_SetVim(_("internal error: failed to get vim list item"));
1034 return NULL;
1035 }
1036 return ConvertToPyObject(&li->li_tv);
1037}
1038
1039#define PROC_RANGE \
1040 if (last < 0) {\
1041 if (last < -size) \
1042 last = 0; \
1043 else \
1044 last += size; \
1045 } \
1046 if (first < 0) \
1047 first = 0; \
1048 if (first > size) \
1049 first = size; \
1050 if (last > size) \
1051 last = size;
1052
1053 static PyObject *
1054ListSlice(PyObject *self, Py_ssize_t first, Py_ssize_t last)
1055{
1056 PyInt i;
1057 PyInt size = ListLength(self);
1058 PyInt n;
1059 PyObject *list;
1060 int reversed = 0;
1061
1062 PROC_RANGE
1063 if (first >= last)
1064 first = last;
1065
1066 n = last-first;
1067 list = PyList_New(n);
1068 if (list == NULL)
1069 return NULL;
1070
1071 for (i = 0; i < n; ++i)
1072 {
1073 PyObject *item = ListItem(self, i);
1074 if (item == NULL)
1075 {
1076 Py_DECREF(list);
1077 return NULL;
1078 }
1079
1080 if ((PyList_SetItem(list, ((reversed)?(n-i-1):(i)), item)))
1081 {
1082 Py_DECREF(item);
1083 Py_DECREF(list);
1084 return NULL;
1085 }
1086 }
1087
1088 return list;
1089}
1090
1091 static int
1092ListAssItem(PyObject *self, Py_ssize_t index, PyObject *obj)
1093{
1094 typval_T tv;
1095 list_T *l = ((ListObject *) (self))->list;
1096 listitem_T *li;
1097 Py_ssize_t length = ListLength(self);
1098
1099 if (l->lv_lock)
1100 {
1101 PyErr_SetVim(_("list is locked"));
1102 return -1;
1103 }
1104 if (index>length || (index==length && obj==NULL))
1105 {
1106 PyErr_SetString(PyExc_IndexError, "list index out of range");
1107 return -1;
1108 }
1109
1110 if (obj == NULL)
1111 {
1112 li = list_find(l, (long) index);
1113 list_remove(l, li, li);
1114 clear_tv(&li->li_tv);
1115 vim_free(li);
1116 return 0;
1117 }
1118
1119 if (ConvertFromPyObject(obj, &tv) == -1)
1120 return -1;
1121
1122 if (index == length)
1123 {
1124 if (list_append_tv(l, &tv) == FAIL)
1125 {
1126 PyErr_SetVim(_("Failed to add item to list"));
1127 return -1;
1128 }
1129 }
1130 else
1131 {
1132 li = list_find(l, (long) index);
1133 clear_tv(&li->li_tv);
1134 copy_tv(&tv, &li->li_tv);
1135 }
1136 return 0;
1137}
1138
1139 static int
1140ListAssSlice(PyObject *self, Py_ssize_t first, Py_ssize_t last, PyObject *obj)
1141{
1142 PyInt size = ListLength(self);
1143 Py_ssize_t i;
1144 Py_ssize_t lsize;
1145 PyObject *litem;
1146 listitem_T *li;
1147 listitem_T *next;
1148 typval_T v;
1149 list_T *l = ((ListObject *) (self))->list;
1150
1151 if (l->lv_lock)
1152 {
1153 PyErr_SetVim(_("list is locked"));
1154 return -1;
1155 }
1156
1157 PROC_RANGE
1158
1159 if (first == size)
1160 li = NULL;
1161 else
1162 {
1163 li = list_find(l, (long) first);
1164 if (li == NULL)
1165 {
1166 PyErr_SetVim(_("internal error: no vim list item"));
1167 return -1;
1168 }
1169 if (last > first)
1170 {
1171 i = last - first;
1172 while (i-- && li != NULL)
1173 {
1174 next = li->li_next;
1175 listitem_remove(l, li);
1176 li = next;
1177 }
1178 }
1179 }
1180
1181 if (obj == NULL)
1182 return 0;
1183
1184 if (!PyList_Check(obj))
1185 {
1186 PyErr_SetString(PyExc_TypeError, _("can only assign lists to slice"));
1187 return -1;
1188 }
1189
1190 lsize = PyList_Size(obj);
1191
1192 for(i=0; i<lsize; i++)
1193 {
1194 litem = PyList_GetItem(obj, i);
1195 if (litem == NULL)
1196 return -1;
1197 if (ConvertFromPyObject(litem, &v) == -1)
1198 return -1;
1199 if (list_insert_tv(l, &v, li) == FAIL)
1200 {
1201 PyErr_SetVim(_("internal error: failed to add item to list"));
1202 return -1;
1203 }
1204 }
1205 return 0;
1206}
1207
1208 static PyObject *
1209ListConcatInPlace(PyObject *self, PyObject *obj)
1210{
1211 list_T *l = ((ListObject *) (self))->list;
1212 PyObject *lookup_dict;
1213
1214 if (l->lv_lock)
1215 {
1216 PyErr_SetVim(_("list is locked"));
1217 return NULL;
1218 }
1219
1220 if (!PySequence_Check(obj))
1221 {
1222 PyErr_SetString(PyExc_TypeError, _("can only concatenate with lists"));
1223 return NULL;
1224 }
1225
1226 lookup_dict = PyDict_New();
1227 if (list_py_concat(l, obj, lookup_dict) == -1)
1228 {
1229 Py_DECREF(lookup_dict);
1230 return NULL;
1231 }
1232 Py_DECREF(lookup_dict);
1233
1234 Py_INCREF(self);
1235 return self;
1236}
1237
1238static struct PyMethodDef ListMethods[] = {
1239 {"extend", (PyCFunction)ListConcatInPlace, METH_O, ""},
1240 { NULL, NULL, 0, NULL }
1241};
1242
1243typedef struct
1244{
1245 PyObject_HEAD
1246 char_u *name;
1247} FunctionObject;
1248
1249static PyTypeObject FunctionType;
1250
1251 static PyObject *
1252FunctionNew(char_u *name)
1253{
1254 FunctionObject *self;
1255
1256 self = PyObject_NEW(FunctionObject, &FunctionType);
1257 if (self == NULL)
1258 return NULL;
1259 self->name = PyMem_New(char_u, STRLEN(name) + 1);
1260 if (self->name == NULL)
1261 {
1262 PyErr_NoMemory();
1263 return NULL;
1264 }
1265 STRCPY(self->name, name);
1266 func_ref(name);
1267 return (PyObject *)(self);
1268}
1269
1270 static PyObject *
1271FunctionCall(PyObject *self, PyObject *argsObject, PyObject *kwargs)
1272{
1273 FunctionObject *this = (FunctionObject *)(self);
1274 char_u *name = this->name;
1275 typval_T args;
1276 typval_T selfdicttv;
1277 typval_T rettv;
1278 dict_T *selfdict = NULL;
1279 PyObject *selfdictObject;
1280 PyObject *result;
1281 int error;
1282
1283 if (ConvertFromPyObject(argsObject, &args) == -1)
1284 return NULL;
1285
1286 if (kwargs != NULL)
1287 {
1288 selfdictObject = PyDict_GetItemString(kwargs, "self");
1289 if (selfdictObject != NULL)
1290 {
Bram Moolenaar9581b5f2012-07-25 15:36:04 +02001291 if (!PyMapping_Check(selfdictObject))
Bram Moolenaardb913952012-06-29 12:54:53 +02001292 {
Bram Moolenaar9581b5f2012-07-25 15:36:04 +02001293 PyErr_SetString(PyExc_TypeError,
1294 _("'self' argument must be a dictionary"));
Bram Moolenaardb913952012-06-29 12:54:53 +02001295 clear_tv(&args);
1296 return NULL;
1297 }
1298 if (ConvertFromPyObject(selfdictObject, &selfdicttv) == -1)
1299 return NULL;
1300 selfdict = selfdicttv.vval.v_dict;
1301 }
1302 }
1303
1304 error = func_call(name, &args, selfdict, &rettv);
1305 if (error != OK)
1306 {
1307 result = NULL;
1308 PyErr_SetVim(_("failed to run function"));
1309 }
1310 else
1311 result = ConvertToPyObject(&rettv);
1312
1313 /* FIXME Check what should really be cleared. */
1314 clear_tv(&args);
1315 clear_tv(&rettv);
1316 /*
1317 * if (selfdict!=NULL)
1318 * clear_tv(selfdicttv);
1319 */
1320
1321 return result;
1322}
1323
1324static struct PyMethodDef FunctionMethods[] = {
1325 {"__call__", (PyCFunction)FunctionCall, METH_VARARGS|METH_KEYWORDS, ""},
1326 { NULL, NULL, 0, NULL }
1327};
1328
Bram Moolenaarca8a4df2010-07-31 19:54:14 +02001329#define INVALID_WINDOW_VALUE ((win_T *)(-1))
1330
1331 static int
1332CheckWindow(WindowObject *this)
1333{
1334 if (this->win == INVALID_WINDOW_VALUE)
1335 {
1336 PyErr_SetVim(_("attempt to refer to deleted window"));
1337 return -1;
1338 }
1339
1340 return 0;
1341}
1342
1343static int WindowSetattr(PyObject *, char *, PyObject *);
1344static PyObject *WindowRepr(PyObject *);
1345
1346 static int
1347WindowSetattr(PyObject *self, char *name, PyObject *val)
1348{
1349 WindowObject *this = (WindowObject *)(self);
1350
1351 if (CheckWindow(this))
1352 return -1;
1353
1354 if (strcmp(name, "buffer") == 0)
1355 {
1356 PyErr_SetString(PyExc_TypeError, _("readonly attribute"));
1357 return -1;
1358 }
1359 else if (strcmp(name, "cursor") == 0)
1360 {
1361 long lnum;
1362 long col;
Bram Moolenaarca8a4df2010-07-31 19:54:14 +02001363
1364 if (!PyArg_Parse(val, "(ll)", &lnum, &col))
1365 return -1;
1366
1367 if (lnum <= 0 || lnum > this->win->w_buffer->b_ml.ml_line_count)
1368 {
1369 PyErr_SetVim(_("cursor position outside buffer"));
1370 return -1;
1371 }
1372
1373 /* Check for keyboard interrupts */
1374 if (VimErrorCheck())
1375 return -1;
1376
Bram Moolenaarca8a4df2010-07-31 19:54:14 +02001377 this->win->w_cursor.lnum = lnum;
1378 this->win->w_cursor.col = col;
1379#ifdef FEAT_VIRTUALEDIT
1380 this->win->w_cursor.coladd = 0;
1381#endif
Bram Moolenaar03a807a2011-07-07 15:08:58 +02001382 /* When column is out of range silently correct it. */
1383 check_cursor_col_win(this->win);
Bram Moolenaarca8a4df2010-07-31 19:54:14 +02001384
Bram Moolenaar03a807a2011-07-07 15:08:58 +02001385 update_screen(VALID);
Bram Moolenaarca8a4df2010-07-31 19:54:14 +02001386 return 0;
1387 }
1388 else if (strcmp(name, "height") == 0)
1389 {
1390 int height;
1391 win_T *savewin;
1392
1393 if (!PyArg_Parse(val, "i", &height))
1394 return -1;
1395
1396#ifdef FEAT_GUI
1397 need_mouse_correct = TRUE;
1398#endif
1399 savewin = curwin;
1400 curwin = this->win;
1401 win_setheight(height);
1402 curwin = savewin;
1403
1404 /* Check for keyboard interrupts */
1405 if (VimErrorCheck())
1406 return -1;
1407
1408 return 0;
1409 }
1410#ifdef FEAT_VERTSPLIT
1411 else if (strcmp(name, "width") == 0)
1412 {
1413 int width;
1414 win_T *savewin;
1415
1416 if (!PyArg_Parse(val, "i", &width))
1417 return -1;
1418
1419#ifdef FEAT_GUI
1420 need_mouse_correct = TRUE;
1421#endif
1422 savewin = curwin;
1423 curwin = this->win;
1424 win_setwidth(width);
1425 curwin = savewin;
1426
1427 /* Check for keyboard interrupts */
1428 if (VimErrorCheck())
1429 return -1;
1430
1431 return 0;
1432 }
1433#endif
1434 else
1435 {
1436 PyErr_SetString(PyExc_AttributeError, name);
1437 return -1;
1438 }
1439}
1440
1441 static PyObject *
1442WindowRepr(PyObject *self)
1443{
1444 static char repr[100];
1445 WindowObject *this = (WindowObject *)(self);
1446
1447 if (this->win == INVALID_WINDOW_VALUE)
1448 {
1449 vim_snprintf(repr, 100, _("<window object (deleted) at %p>"), (self));
1450 return PyString_FromString(repr);
1451 }
1452 else
1453 {
1454 int i = 0;
1455 win_T *w;
1456
1457 for (w = firstwin; w != NULL && w != this->win; w = W_NEXT(w))
1458 ++i;
1459
1460 if (w == NULL)
1461 vim_snprintf(repr, 100, _("<window object (unknown) at %p>"),
1462 (self));
1463 else
1464 vim_snprintf(repr, 100, _("<window %d>"), i);
1465
1466 return PyString_FromString(repr);
1467 }
1468}
1469
1470/*
1471 * Window list object - Implementation
1472 */
1473 static PyInt
1474WinListLength(PyObject *self UNUSED)
1475{
1476 win_T *w = firstwin;
1477 PyInt n = 0;
1478
1479 while (w != NULL)
1480 {
1481 ++n;
1482 w = W_NEXT(w);
1483 }
1484
1485 return n;
1486}
1487
1488 static PyObject *
1489WinListItem(PyObject *self UNUSED, PyInt n)
1490{
1491 win_T *w;
1492
1493 for (w = firstwin; w != NULL; w = W_NEXT(w), --n)
1494 if (n == 0)
1495 return WindowNew(w);
1496
1497 PyErr_SetString(PyExc_IndexError, _("no such window"));
1498 return NULL;
1499}
1500
1501/* Convert a Python string into a Vim line.
1502 *
1503 * The result is in allocated memory. All internal nulls are replaced by
1504 * newline characters. It is an error for the string to contain newline
1505 * characters.
1506 *
1507 * On errors, the Python exception data is set, and NULL is returned.
1508 */
1509 static char *
1510StringToLine(PyObject *obj)
1511{
1512 const char *str;
1513 char *save;
Bram Moolenaar19e60942011-06-19 00:27:51 +02001514 PyObject *bytes;
Bram Moolenaarca8a4df2010-07-31 19:54:14 +02001515 PyInt len;
1516 PyInt i;
1517 char *p;
1518
1519 if (obj == NULL || !PyString_Check(obj))
1520 {
1521 PyErr_BadArgument();
1522 return NULL;
1523 }
1524
Bram Moolenaar19e60942011-06-19 00:27:51 +02001525 bytes = PyString_AsBytes(obj); /* for Python 2 this does nothing */
1526 str = PyString_AsString(bytes);
1527 len = PyString_Size(bytes);
Bram Moolenaarca8a4df2010-07-31 19:54:14 +02001528
1529 /*
1530 * Error checking: String must not contain newlines, as we
1531 * are replacing a single line, and we must replace it with
1532 * a single line.
1533 * A trailing newline is removed, so that append(f.readlines()) works.
1534 */
1535 p = memchr(str, '\n', len);
1536 if (p != NULL)
1537 {
1538 if (p == str + len - 1)
1539 --len;
1540 else
1541 {
1542 PyErr_SetVim(_("string cannot contain newlines"));
1543 return NULL;
1544 }
1545 }
1546
1547 /* Create a copy of the string, with internal nulls replaced by
1548 * newline characters, as is the vim convention.
1549 */
1550 save = (char *)alloc((unsigned)(len+1));
1551 if (save == NULL)
1552 {
1553 PyErr_NoMemory();
1554 return NULL;
1555 }
1556
1557 for (i = 0; i < len; ++i)
1558 {
1559 if (str[i] == '\0')
1560 save[i] = '\n';
1561 else
1562 save[i] = str[i];
1563 }
1564
1565 save[i] = '\0';
Bram Moolenaar19e60942011-06-19 00:27:51 +02001566 PyString_FreeBytes(bytes); /* Python 2 does nothing here */
Bram Moolenaarca8a4df2010-07-31 19:54:14 +02001567
1568 return save;
1569}
1570
1571/* Get a line from the specified buffer. The line number is
1572 * in Vim format (1-based). The line is returned as a Python
1573 * string object.
1574 */
1575 static PyObject *
1576GetBufferLine(buf_T *buf, PyInt n)
1577{
1578 return LineToString((char *)ml_get_buf(buf, (linenr_T)n, FALSE));
1579}
1580
1581
1582/* Get a list of lines from the specified buffer. The line numbers
1583 * are in Vim format (1-based). The range is from lo up to, but not
1584 * including, hi. The list is returned as a Python list of string objects.
1585 */
1586 static PyObject *
1587GetBufferLineList(buf_T *buf, PyInt lo, PyInt hi)
1588{
1589 PyInt i;
1590 PyInt n = hi - lo;
1591 PyObject *list = PyList_New(n);
1592
1593 if (list == NULL)
1594 return NULL;
1595
1596 for (i = 0; i < n; ++i)
1597 {
1598 PyObject *str = LineToString((char *)ml_get_buf(buf, (linenr_T)(lo+i), FALSE));
1599
1600 /* Error check - was the Python string creation OK? */
1601 if (str == NULL)
1602 {
1603 Py_DECREF(list);
1604 return NULL;
1605 }
1606
1607 /* Set the list item */
1608 if (PyList_SetItem(list, i, str))
1609 {
1610 Py_DECREF(str);
1611 Py_DECREF(list);
1612 return NULL;
1613 }
1614 }
1615
1616 /* The ownership of the Python list is passed to the caller (ie,
1617 * the caller should Py_DECREF() the object when it is finished
1618 * with it).
1619 */
1620
1621 return list;
1622}
1623
1624/*
1625 * Check if deleting lines made the cursor position invalid.
1626 * Changed the lines from "lo" to "hi" and added "extra" lines (negative if
1627 * deleted).
1628 */
1629 static void
1630py_fix_cursor(linenr_T lo, linenr_T hi, linenr_T extra)
1631{
1632 if (curwin->w_cursor.lnum >= lo)
1633 {
1634 /* Adjust the cursor position if it's in/after the changed
1635 * lines. */
1636 if (curwin->w_cursor.lnum >= hi)
1637 {
1638 curwin->w_cursor.lnum += extra;
1639 check_cursor_col();
1640 }
1641 else if (extra < 0)
1642 {
1643 curwin->w_cursor.lnum = lo;
1644 check_cursor();
1645 }
1646 else
1647 check_cursor_col();
1648 changed_cline_bef_curs();
1649 }
1650 invalidate_botline();
1651}
1652
Bram Moolenaar19e60942011-06-19 00:27:51 +02001653/*
1654 * Replace a line in the specified buffer. The line number is
Bram Moolenaarca8a4df2010-07-31 19:54:14 +02001655 * in Vim format (1-based). The replacement line is given as
1656 * a Python string object. The object is checked for validity
1657 * and correct format. Errors are returned as a value of FAIL.
1658 * The return value is OK on success.
1659 * If OK is returned and len_change is not NULL, *len_change
1660 * is set to the change in the buffer length.
1661 */
1662 static int
1663SetBufferLine(buf_T *buf, PyInt n, PyObject *line, PyInt *len_change)
1664{
1665 /* First of all, we check the thpe of the supplied Python object.
1666 * There are three cases:
1667 * 1. NULL, or None - this is a deletion.
1668 * 2. A string - this is a replacement.
1669 * 3. Anything else - this is an error.
1670 */
1671 if (line == Py_None || line == NULL)
1672 {
1673 buf_T *savebuf = curbuf;
1674
1675 PyErr_Clear();
1676 curbuf = buf;
1677
1678 if (u_savedel((linenr_T)n, 1L) == FAIL)
1679 PyErr_SetVim(_("cannot save undo information"));
1680 else if (ml_delete((linenr_T)n, FALSE) == FAIL)
1681 PyErr_SetVim(_("cannot delete line"));
1682 else
1683 {
1684 if (buf == curwin->w_buffer)
1685 py_fix_cursor((linenr_T)n, (linenr_T)n + 1, (linenr_T)-1);
1686 deleted_lines_mark((linenr_T)n, 1L);
1687 }
1688
1689 curbuf = savebuf;
1690
1691 if (PyErr_Occurred() || VimErrorCheck())
1692 return FAIL;
1693
1694 if (len_change)
1695 *len_change = -1;
1696
1697 return OK;
1698 }
1699 else if (PyString_Check(line))
1700 {
1701 char *save = StringToLine(line);
1702 buf_T *savebuf = curbuf;
1703
1704 if (save == NULL)
1705 return FAIL;
1706
1707 /* We do not need to free "save" if ml_replace() consumes it. */
1708 PyErr_Clear();
1709 curbuf = buf;
1710
1711 if (u_savesub((linenr_T)n) == FAIL)
1712 {
1713 PyErr_SetVim(_("cannot save undo information"));
1714 vim_free(save);
1715 }
1716 else if (ml_replace((linenr_T)n, (char_u *)save, FALSE) == FAIL)
1717 {
1718 PyErr_SetVim(_("cannot replace line"));
1719 vim_free(save);
1720 }
1721 else
1722 changed_bytes((linenr_T)n, 0);
1723
1724 curbuf = savebuf;
1725
1726 /* Check that the cursor is not beyond the end of the line now. */
1727 if (buf == curwin->w_buffer)
1728 check_cursor_col();
1729
1730 if (PyErr_Occurred() || VimErrorCheck())
1731 return FAIL;
1732
1733 if (len_change)
1734 *len_change = 0;
1735
1736 return OK;
1737 }
1738 else
1739 {
1740 PyErr_BadArgument();
1741 return FAIL;
1742 }
1743}
1744
Bram Moolenaar19e60942011-06-19 00:27:51 +02001745/* Replace a range of lines in the specified buffer. The line numbers are in
1746 * Vim format (1-based). The range is from lo up to, but not including, hi.
1747 * The replacement lines are given as a Python list of string objects. The
1748 * list is checked for validity and correct format. Errors are returned as a
1749 * value of FAIL. The return value is OK on success.
1750 * If OK is returned and len_change is not NULL, *len_change
1751 * is set to the change in the buffer length.
1752 */
1753 static int
1754SetBufferLineList(buf_T *buf, PyInt lo, PyInt hi, PyObject *list, PyInt *len_change)
1755{
1756 /* First of all, we check the thpe of the supplied Python object.
1757 * There are three cases:
1758 * 1. NULL, or None - this is a deletion.
1759 * 2. A list - this is a replacement.
1760 * 3. Anything else - this is an error.
1761 */
1762 if (list == Py_None || list == NULL)
1763 {
1764 PyInt i;
1765 PyInt n = (int)(hi - lo);
1766 buf_T *savebuf = curbuf;
1767
1768 PyErr_Clear();
1769 curbuf = buf;
1770
1771 if (u_savedel((linenr_T)lo, (long)n) == FAIL)
1772 PyErr_SetVim(_("cannot save undo information"));
1773 else
1774 {
1775 for (i = 0; i < n; ++i)
1776 {
1777 if (ml_delete((linenr_T)lo, FALSE) == FAIL)
1778 {
1779 PyErr_SetVim(_("cannot delete line"));
1780 break;
1781 }
1782 }
1783 if (buf == curwin->w_buffer)
1784 py_fix_cursor((linenr_T)lo, (linenr_T)hi, (linenr_T)-n);
1785 deleted_lines_mark((linenr_T)lo, (long)i);
1786 }
1787
1788 curbuf = savebuf;
1789
1790 if (PyErr_Occurred() || VimErrorCheck())
1791 return FAIL;
1792
1793 if (len_change)
1794 *len_change = -n;
1795
1796 return OK;
1797 }
1798 else if (PyList_Check(list))
1799 {
1800 PyInt i;
1801 PyInt new_len = PyList_Size(list);
1802 PyInt old_len = hi - lo;
1803 PyInt extra = 0; /* lines added to text, can be negative */
1804 char **array;
1805 buf_T *savebuf;
1806
1807 if (new_len == 0) /* avoid allocating zero bytes */
1808 array = NULL;
1809 else
1810 {
1811 array = (char **)alloc((unsigned)(new_len * sizeof(char *)));
1812 if (array == NULL)
1813 {
1814 PyErr_NoMemory();
1815 return FAIL;
1816 }
1817 }
1818
1819 for (i = 0; i < new_len; ++i)
1820 {
1821 PyObject *line = PyList_GetItem(list, i);
1822
1823 array[i] = StringToLine(line);
1824 if (array[i] == NULL)
1825 {
1826 while (i)
1827 vim_free(array[--i]);
1828 vim_free(array);
1829 return FAIL;
1830 }
1831 }
1832
1833 savebuf = curbuf;
1834
1835 PyErr_Clear();
1836 curbuf = buf;
1837
1838 if (u_save((linenr_T)(lo-1), (linenr_T)hi) == FAIL)
1839 PyErr_SetVim(_("cannot save undo information"));
1840
1841 /* If the size of the range is reducing (ie, new_len < old_len) we
1842 * need to delete some old_len. We do this at the start, by
1843 * repeatedly deleting line "lo".
1844 */
1845 if (!PyErr_Occurred())
1846 {
1847 for (i = 0; i < old_len - new_len; ++i)
1848 if (ml_delete((linenr_T)lo, FALSE) == FAIL)
1849 {
1850 PyErr_SetVim(_("cannot delete line"));
1851 break;
1852 }
1853 extra -= i;
1854 }
1855
1856 /* For as long as possible, replace the existing old_len with the
1857 * new old_len. This is a more efficient operation, as it requires
1858 * less memory allocation and freeing.
1859 */
1860 if (!PyErr_Occurred())
1861 {
1862 for (i = 0; i < old_len && i < new_len; ++i)
1863 if (ml_replace((linenr_T)(lo+i), (char_u *)array[i], FALSE)
1864 == FAIL)
1865 {
1866 PyErr_SetVim(_("cannot replace line"));
1867 break;
1868 }
1869 }
1870 else
1871 i = 0;
1872
1873 /* Now we may need to insert the remaining new old_len. If we do, we
1874 * must free the strings as we finish with them (we can't pass the
1875 * responsibility to vim in this case).
1876 */
1877 if (!PyErr_Occurred())
1878 {
1879 while (i < new_len)
1880 {
1881 if (ml_append((linenr_T)(lo + i - 1),
1882 (char_u *)array[i], 0, FALSE) == FAIL)
1883 {
1884 PyErr_SetVim(_("cannot insert line"));
1885 break;
1886 }
1887 vim_free(array[i]);
1888 ++i;
1889 ++extra;
1890 }
1891 }
1892
1893 /* Free any left-over old_len, as a result of an error */
1894 while (i < new_len)
1895 {
1896 vim_free(array[i]);
1897 ++i;
1898 }
1899
1900 /* Free the array of old_len. All of its contents have now
1901 * been dealt with (either freed, or the responsibility passed
1902 * to vim.
1903 */
1904 vim_free(array);
1905
1906 /* Adjust marks. Invalidate any which lie in the
1907 * changed range, and move any in the remainder of the buffer.
1908 */
1909 mark_adjust((linenr_T)lo, (linenr_T)(hi - 1),
1910 (long)MAXLNUM, (long)extra);
1911 changed_lines((linenr_T)lo, 0, (linenr_T)hi, (long)extra);
1912
1913 if (buf == curwin->w_buffer)
1914 py_fix_cursor((linenr_T)lo, (linenr_T)hi, (linenr_T)extra);
1915
1916 curbuf = savebuf;
1917
1918 if (PyErr_Occurred() || VimErrorCheck())
1919 return FAIL;
1920
1921 if (len_change)
1922 *len_change = new_len - old_len;
1923
1924 return OK;
1925 }
1926 else
1927 {
1928 PyErr_BadArgument();
1929 return FAIL;
1930 }
1931}
Bram Moolenaarca8a4df2010-07-31 19:54:14 +02001932
1933/* Insert a number of lines into the specified buffer after the specifed line.
1934 * The line number is in Vim format (1-based). The lines to be inserted are
1935 * given as a Python list of string objects or as a single string. The lines
1936 * to be added are checked for validity and correct format. Errors are
1937 * returned as a value of FAIL. The return value is OK on success.
1938 * If OK is returned and len_change is not NULL, *len_change
1939 * is set to the change in the buffer length.
1940 */
1941 static int
1942InsertBufferLines(buf_T *buf, PyInt n, PyObject *lines, PyInt *len_change)
1943{
1944 /* First of all, we check the type of the supplied Python object.
1945 * It must be a string or a list, or the call is in error.
1946 */
1947 if (PyString_Check(lines))
1948 {
1949 char *str = StringToLine(lines);
1950 buf_T *savebuf;
1951
1952 if (str == NULL)
1953 return FAIL;
1954
1955 savebuf = curbuf;
1956
1957 PyErr_Clear();
1958 curbuf = buf;
1959
1960 if (u_save((linenr_T)n, (linenr_T)(n+1)) == FAIL)
1961 PyErr_SetVim(_("cannot save undo information"));
1962 else if (ml_append((linenr_T)n, (char_u *)str, 0, FALSE) == FAIL)
1963 PyErr_SetVim(_("cannot insert line"));
1964 else
1965 appended_lines_mark((linenr_T)n, 1L);
1966
1967 vim_free(str);
1968 curbuf = savebuf;
1969 update_screen(VALID);
1970
1971 if (PyErr_Occurred() || VimErrorCheck())
1972 return FAIL;
1973
1974 if (len_change)
1975 *len_change = 1;
1976
1977 return OK;
1978 }
1979 else if (PyList_Check(lines))
1980 {
1981 PyInt i;
1982 PyInt size = PyList_Size(lines);
1983 char **array;
1984 buf_T *savebuf;
1985
1986 array = (char **)alloc((unsigned)(size * sizeof(char *)));
1987 if (array == NULL)
1988 {
1989 PyErr_NoMemory();
1990 return FAIL;
1991 }
1992
1993 for (i = 0; i < size; ++i)
1994 {
1995 PyObject *line = PyList_GetItem(lines, i);
1996 array[i] = StringToLine(line);
1997
1998 if (array[i] == NULL)
1999 {
2000 while (i)
2001 vim_free(array[--i]);
2002 vim_free(array);
2003 return FAIL;
2004 }
2005 }
2006
2007 savebuf = curbuf;
2008
2009 PyErr_Clear();
2010 curbuf = buf;
2011
2012 if (u_save((linenr_T)n, (linenr_T)(n + 1)) == FAIL)
2013 PyErr_SetVim(_("cannot save undo information"));
2014 else
2015 {
2016 for (i = 0; i < size; ++i)
2017 {
2018 if (ml_append((linenr_T)(n + i),
2019 (char_u *)array[i], 0, FALSE) == FAIL)
2020 {
2021 PyErr_SetVim(_("cannot insert line"));
2022
2023 /* Free the rest of the lines */
2024 while (i < size)
2025 vim_free(array[i++]);
2026
2027 break;
2028 }
2029 vim_free(array[i]);
2030 }
2031 if (i > 0)
2032 appended_lines_mark((linenr_T)n, (long)i);
2033 }
2034
2035 /* Free the array of lines. All of its contents have now
2036 * been freed.
2037 */
2038 vim_free(array);
2039
2040 curbuf = savebuf;
2041 update_screen(VALID);
2042
2043 if (PyErr_Occurred() || VimErrorCheck())
2044 return FAIL;
2045
2046 if (len_change)
2047 *len_change = size;
2048
2049 return OK;
2050 }
2051 else
2052 {
2053 PyErr_BadArgument();
2054 return FAIL;
2055 }
2056}
2057
2058/*
2059 * Common routines for buffers and line ranges
2060 * -------------------------------------------
2061 */
2062
2063 static int
2064CheckBuffer(BufferObject *this)
2065{
2066 if (this->buf == INVALID_BUFFER_VALUE)
2067 {
2068 PyErr_SetVim(_("attempt to refer to deleted buffer"));
2069 return -1;
2070 }
2071
2072 return 0;
2073}
2074
2075 static PyObject *
2076RBItem(BufferObject *self, PyInt n, PyInt start, PyInt end)
2077{
2078 if (CheckBuffer(self))
2079 return NULL;
2080
2081 if (n < 0 || n > end - start)
2082 {
2083 PyErr_SetString(PyExc_IndexError, _("line number out of range"));
2084 return NULL;
2085 }
2086
2087 return GetBufferLine(self->buf, n+start);
2088}
2089
2090 static PyObject *
2091RBSlice(BufferObject *self, PyInt lo, PyInt hi, PyInt start, PyInt end)
2092{
2093 PyInt size;
2094
2095 if (CheckBuffer(self))
2096 return NULL;
2097
2098 size = end - start + 1;
2099
2100 if (lo < 0)
2101 lo = 0;
2102 else if (lo > size)
2103 lo = size;
2104 if (hi < 0)
2105 hi = 0;
2106 if (hi < lo)
2107 hi = lo;
2108 else if (hi > size)
2109 hi = size;
2110
2111 return GetBufferLineList(self->buf, lo+start, hi+start);
2112}
2113
2114 static PyInt
2115RBAsItem(BufferObject *self, PyInt n, PyObject *val, PyInt start, PyInt end, PyInt *new_end)
2116{
2117 PyInt len_change;
2118
2119 if (CheckBuffer(self))
2120 return -1;
2121
2122 if (n < 0 || n > end - start)
2123 {
2124 PyErr_SetString(PyExc_IndexError, _("line number out of range"));
2125 return -1;
2126 }
2127
2128 if (SetBufferLine(self->buf, n+start, val, &len_change) == FAIL)
2129 return -1;
2130
2131 if (new_end)
2132 *new_end = end + len_change;
2133
2134 return 0;
2135}
2136
Bram Moolenaar19e60942011-06-19 00:27:51 +02002137 static PyInt
2138RBAsSlice(BufferObject *self, PyInt lo, PyInt hi, PyObject *val, PyInt start, PyInt end, PyInt *new_end)
2139{
2140 PyInt size;
2141 PyInt len_change;
2142
2143 /* Self must be a valid buffer */
2144 if (CheckBuffer(self))
2145 return -1;
2146
2147 /* Sort out the slice range */
2148 size = end - start + 1;
2149
2150 if (lo < 0)
2151 lo = 0;
2152 else if (lo > size)
2153 lo = size;
2154 if (hi < 0)
2155 hi = 0;
2156 if (hi < lo)
2157 hi = lo;
2158 else if (hi > size)
2159 hi = size;
2160
2161 if (SetBufferLineList(self->buf, lo + start, hi + start,
2162 val, &len_change) == FAIL)
2163 return -1;
2164
2165 if (new_end)
2166 *new_end = end + len_change;
2167
2168 return 0;
2169}
2170
Bram Moolenaarca8a4df2010-07-31 19:54:14 +02002171
2172 static PyObject *
2173RBAppend(BufferObject *self, PyObject *args, PyInt start, PyInt end, PyInt *new_end)
2174{
2175 PyObject *lines;
2176 PyInt len_change;
2177 PyInt max;
2178 PyInt n;
2179
2180 if (CheckBuffer(self))
2181 return NULL;
2182
2183 max = n = end - start + 1;
2184
2185 if (!PyArg_ParseTuple(args, "O|n", &lines, &n))
2186 return NULL;
2187
2188 if (n < 0 || n > max)
2189 {
2190 PyErr_SetString(PyExc_ValueError, _("line number out of range"));
2191 return NULL;
2192 }
2193
2194 if (InsertBufferLines(self->buf, n + start - 1, lines, &len_change) == FAIL)
2195 return NULL;
2196
2197 if (new_end)
2198 *new_end = end + len_change;
2199
2200 Py_INCREF(Py_None);
2201 return Py_None;
2202}
2203
2204
2205/* Buffer object - Definitions
2206 */
2207
2208typedef struct
2209{
2210 PyObject_HEAD
2211 BufferObject *buf;
2212 PyInt start;
2213 PyInt end;
2214} RangeObject;
2215
2216 static PyObject *
2217RangeNew(buf_T *buf, PyInt start, PyInt end)
2218{
2219 BufferObject *bufr;
2220 RangeObject *self;
2221 self = PyObject_NEW(RangeObject, &RangeType);
2222 if (self == NULL)
2223 return NULL;
2224
2225 bufr = (BufferObject *)BufferNew(buf);
2226 if (bufr == NULL)
2227 {
2228 Py_DECREF(self);
2229 return NULL;
2230 }
2231 Py_INCREF(bufr);
2232
2233 self->buf = bufr;
2234 self->start = start;
2235 self->end = end;
2236
2237 return (PyObject *)(self);
2238}
2239
2240 static PyObject *
2241BufferAppend(PyObject *self, PyObject *args)
2242{
2243 return RBAppend((BufferObject *)(self), args, 1,
2244 (PyInt)((BufferObject *)(self))->buf->b_ml.ml_line_count,
2245 NULL);
2246}
2247
2248 static PyObject *
2249BufferMark(PyObject *self, PyObject *args)
2250{
2251 pos_T *posp;
2252 char *pmark;
2253 char mark;
2254 buf_T *curbuf_save;
2255
2256 if (CheckBuffer((BufferObject *)(self)))
2257 return NULL;
2258
2259 if (!PyArg_ParseTuple(args, "s", &pmark))
2260 return NULL;
2261 mark = *pmark;
2262
2263 curbuf_save = curbuf;
2264 curbuf = ((BufferObject *)(self))->buf;
2265 posp = getmark(mark, FALSE);
2266 curbuf = curbuf_save;
2267
2268 if (posp == NULL)
2269 {
2270 PyErr_SetVim(_("invalid mark name"));
2271 return NULL;
2272 }
2273
2274 /* Ckeck for keyboard interrupt */
2275 if (VimErrorCheck())
2276 return NULL;
2277
2278 if (posp->lnum <= 0)
2279 {
2280 /* Or raise an error? */
2281 Py_INCREF(Py_None);
2282 return Py_None;
2283 }
2284
2285 return Py_BuildValue("(ll)", (long)(posp->lnum), (long)(posp->col));
2286}
2287
2288 static PyObject *
2289BufferRange(PyObject *self, PyObject *args)
2290{
2291 PyInt start;
2292 PyInt end;
2293
2294 if (CheckBuffer((BufferObject *)(self)))
2295 return NULL;
2296
2297 if (!PyArg_ParseTuple(args, "nn", &start, &end))
2298 return NULL;
2299
2300 return RangeNew(((BufferObject *)(self))->buf, start, end);
2301}
2302
2303static struct PyMethodDef BufferMethods[] = {
2304 /* name, function, calling, documentation */
2305 {"append", BufferAppend, 1, "Append data to Vim buffer" },
2306 {"mark", BufferMark, 1, "Return (row,col) representing position of named mark" },
2307 {"range", BufferRange, 1, "Return a range object which represents the part of the given buffer between line numbers s and e" },
Bram Moolenaar7f85d292012-02-04 20:17:26 +01002308#if PY_VERSION_HEX >= 0x03000000
2309 {"__dir__", BufferDir, 4, "List its attributes" },
2310#endif
Bram Moolenaarca8a4df2010-07-31 19:54:14 +02002311 { NULL, NULL, 0, NULL }
2312};
2313
2314 static PyObject *
2315RangeAppend(PyObject *self, PyObject *args)
2316{
2317 return RBAppend(((RangeObject *)(self))->buf, args,
2318 ((RangeObject *)(self))->start,
2319 ((RangeObject *)(self))->end,
2320 &((RangeObject *)(self))->end);
2321}
2322
2323 static PyInt
2324RangeLength(PyObject *self)
2325{
2326 /* HOW DO WE SIGNAL AN ERROR FROM THIS FUNCTION? */
2327 if (CheckBuffer(((RangeObject *)(self))->buf))
2328 return -1; /* ??? */
2329
2330 return (((RangeObject *)(self))->end - ((RangeObject *)(self))->start + 1);
2331}
2332
2333 static PyObject *
2334RangeItem(PyObject *self, PyInt n)
2335{
2336 return RBItem(((RangeObject *)(self))->buf, n,
2337 ((RangeObject *)(self))->start,
2338 ((RangeObject *)(self))->end);
2339}
2340
2341 static PyObject *
2342RangeRepr(PyObject *self)
2343{
2344 static char repr[100];
2345 RangeObject *this = (RangeObject *)(self);
2346
2347 if (this->buf->buf == INVALID_BUFFER_VALUE)
2348 {
2349 vim_snprintf(repr, 100, "<range object (for deleted buffer) at %p>",
2350 (self));
2351 return PyString_FromString(repr);
2352 }
2353 else
2354 {
2355 char *name = (char *)this->buf->buf->b_fname;
2356 int len;
2357
2358 if (name == NULL)
2359 name = "";
2360 len = (int)strlen(name);
2361
2362 if (len > 45)
2363 name = name + (45 - len);
2364
2365 vim_snprintf(repr, 100, "<range %s%s (%d:%d)>",
2366 len > 45 ? "..." : "", name,
2367 this->start, this->end);
2368
2369 return PyString_FromString(repr);
2370 }
2371}
2372
2373 static PyObject *
2374RangeSlice(PyObject *self, PyInt lo, PyInt hi)
2375{
2376 return RBSlice(((RangeObject *)(self))->buf, lo, hi,
2377 ((RangeObject *)(self))->start,
2378 ((RangeObject *)(self))->end);
2379}
2380
2381/*
2382 * Line range object - Definitions
2383 */
2384
2385static struct PyMethodDef RangeMethods[] = {
2386 /* name, function, calling, documentation */
2387 {"append", RangeAppend, 1, "Append data to the Vim range" },
2388 { NULL, NULL, 0, NULL }
2389};
2390
Bram Moolenaardb913952012-06-29 12:54:53 +02002391 static void
2392set_ref_in_py(const int copyID)
2393{
2394 pylinkedlist_T *cur;
2395 dict_T *dd;
2396 list_T *ll;
2397
2398 if (lastdict != NULL)
2399 for(cur = lastdict ; cur != NULL ; cur = cur->pll_prev)
2400 {
2401 dd = ((DictionaryObject *) (cur->pll_obj))->dict;
2402 if (dd->dv_copyID != copyID)
2403 {
2404 dd->dv_copyID = copyID;
2405 set_ref_in_ht(&dd->dv_hashtab, copyID);
2406 }
2407 }
2408
2409 if (lastlist != NULL)
2410 for(cur = lastlist ; cur != NULL ; cur = cur->pll_prev)
2411 {
2412 ll = ((ListObject *) (cur->pll_obj))->list;
2413 if (ll->lv_copyID != copyID)
2414 {
2415 ll->lv_copyID = copyID;
2416 set_ref_in_list(ll, copyID);
2417 }
2418 }
2419}
2420
2421 static int
2422set_string_copy(char_u *str, typval_T *tv)
2423{
2424 tv->vval.v_string = vim_strsave(str);
2425 if (tv->vval.v_string == NULL)
2426 {
2427 PyErr_NoMemory();
2428 return -1;
2429 }
2430 return 0;
2431}
2432
2433#ifdef FEAT_EVAL
2434typedef int (*pytotvfunc)(PyObject *, typval_T *, PyObject *);
2435
2436 static int
2437convert_dl(PyObject *obj, typval_T *tv,
2438 pytotvfunc py_to_tv, PyObject *lookupDict)
2439{
2440 PyObject *capsule;
2441 char hexBuf[sizeof(void *) * 2 + 3];
2442
2443 sprintf(hexBuf, "%p", obj);
2444
Bram Moolenaar2afa3232012-06-29 16:28:28 +02002445# ifdef PY_USE_CAPSULE
Bram Moolenaardb913952012-06-29 12:54:53 +02002446 capsule = PyDict_GetItemString(lookupDict, hexBuf);
Bram Moolenaar2afa3232012-06-29 16:28:28 +02002447# else
Bram Moolenaar221d6872012-06-30 13:34:34 +02002448 capsule = (PyObject *)PyDict_GetItemString(lookupDict, hexBuf);
Bram Moolenaar2afa3232012-06-29 16:28:28 +02002449# endif
Bram Moolenaar221d6872012-06-30 13:34:34 +02002450 if (capsule == NULL)
Bram Moolenaardb913952012-06-29 12:54:53 +02002451 {
Bram Moolenaar2afa3232012-06-29 16:28:28 +02002452# ifdef PY_USE_CAPSULE
Bram Moolenaardb913952012-06-29 12:54:53 +02002453 capsule = PyCapsule_New(tv, NULL, NULL);
Bram Moolenaar221d6872012-06-30 13:34:34 +02002454# else
2455 capsule = PyCObject_FromVoidPtr(tv, NULL);
2456# endif
Bram Moolenaardb913952012-06-29 12:54:53 +02002457 PyDict_SetItemString(lookupDict, hexBuf, capsule);
2458 Py_DECREF(capsule);
2459 if (py_to_tv(obj, tv, lookupDict) == -1)
2460 {
2461 tv->v_type = VAR_UNKNOWN;
2462 return -1;
2463 }
2464 /* As we are not using copy_tv which increments reference count we must
2465 * do it ourself. */
2466 switch(tv->v_type)
2467 {
2468 case VAR_DICT: ++tv->vval.v_dict->dv_refcount; break;
2469 case VAR_LIST: ++tv->vval.v_list->lv_refcount; break;
2470 }
2471 }
2472 else
2473 {
Bram Moolenaar2afa3232012-06-29 16:28:28 +02002474 typval_T *v;
2475
2476# ifdef PY_USE_CAPSULE
2477 v = PyCapsule_GetPointer(capsule, NULL);
2478# else
Bram Moolenaar221d6872012-06-30 13:34:34 +02002479 v = PyCObject_AsVoidPtr(capsule);
Bram Moolenaar2afa3232012-06-29 16:28:28 +02002480# endif
Bram Moolenaardb913952012-06-29 12:54:53 +02002481 copy_tv(v, tv);
2482 }
2483 return 0;
2484}
2485
2486 static int
2487ConvertFromPyObject(PyObject *obj, typval_T *tv)
2488{
2489 PyObject *lookup_dict;
2490 int r;
2491
2492 lookup_dict = PyDict_New();
2493 r = _ConvertFromPyObject(obj, tv, lookup_dict);
2494 Py_DECREF(lookup_dict);
2495 return r;
2496}
2497
2498 static int
2499_ConvertFromPyObject(PyObject *obj, typval_T *tv, PyObject *lookupDict)
2500{
2501 if (obj->ob_type == &DictionaryType)
2502 {
2503 tv->v_type = VAR_DICT;
2504 tv->vval.v_dict = (((DictionaryObject *)(obj))->dict);
2505 ++tv->vval.v_dict->dv_refcount;
2506 }
2507 else if (obj->ob_type == &ListType)
2508 {
2509 tv->v_type = VAR_LIST;
2510 tv->vval.v_list = (((ListObject *)(obj))->list);
2511 ++tv->vval.v_list->lv_refcount;
2512 }
2513 else if (obj->ob_type == &FunctionType)
2514 {
2515 if (set_string_copy(((FunctionObject *) (obj))->name, tv) == -1)
2516 return -1;
2517
2518 tv->v_type = VAR_FUNC;
2519 func_ref(tv->vval.v_string);
2520 }
2521#if PY_MAJOR_VERSION >= 3
2522 else if (PyBytes_Check(obj))
2523 {
2524 char_u *result = (char_u *) PyBytes_AsString(obj);
2525
2526 if (result == NULL)
2527 return -1;
2528
2529 if (set_string_copy(result, tv) == -1)
2530 return -1;
2531
2532 tv->v_type = VAR_STRING;
2533 }
2534 else if (PyUnicode_Check(obj))
2535 {
2536 PyObject *bytes;
2537 char_u *result;
2538
2539 bytes = PyString_AsBytes(obj);
2540 if (bytes == NULL)
2541 return -1;
2542
2543 result = (char_u *) PyBytes_AsString(bytes);
2544 if (result == NULL)
2545 return -1;
2546
2547 if (set_string_copy(result, tv) == -1)
2548 {
2549 Py_XDECREF(bytes);
2550 return -1;
2551 }
2552 Py_XDECREF(bytes);
2553
2554 tv->v_type = VAR_STRING;
2555 }
2556#else
2557 else if (PyUnicode_Check(obj))
2558 {
2559 PyObject *bytes;
2560 char_u *result;
2561
2562 bytes = PyUnicode_AsEncodedString(obj, (char *)ENC_OPT, NULL);
2563 if (bytes == NULL)
2564 return -1;
2565
2566 result=(char_u *) PyString_AsString(bytes);
2567 if (result == NULL)
2568 return -1;
2569
2570 if (set_string_copy(result, tv) == -1)
2571 {
2572 Py_XDECREF(bytes);
2573 return -1;
2574 }
2575 Py_XDECREF(bytes);
2576
2577 tv->v_type = VAR_STRING;
2578 }
2579 else if (PyString_Check(obj))
2580 {
2581 char_u *result = (char_u *) PyString_AsString(obj);
2582
2583 if (result == NULL)
2584 return -1;
2585
2586 if (set_string_copy(result, tv) == -1)
2587 return -1;
2588
2589 tv->v_type = VAR_STRING;
2590 }
2591 else if (PyInt_Check(obj))
2592 {
2593 tv->v_type = VAR_NUMBER;
2594 tv->vval.v_number = (varnumber_T) PyInt_AsLong(obj);
2595 }
2596#endif
2597 else if (PyLong_Check(obj))
2598 {
2599 tv->v_type = VAR_NUMBER;
2600 tv->vval.v_number = (varnumber_T) PyLong_AsLong(obj);
2601 }
2602 else if (PyDict_Check(obj))
2603 return convert_dl(obj, tv, pydict_to_tv, lookupDict);
2604#ifdef FEAT_FLOAT
2605 else if (PyFloat_Check(obj))
2606 {
2607 tv->v_type = VAR_FLOAT;
2608 tv->vval.v_float = (float_T) PyFloat_AsDouble(obj);
2609 }
2610#endif
2611 else if (PyIter_Check(obj))
2612 return convert_dl(obj, tv, pyiter_to_tv, lookupDict);
2613 else if (PySequence_Check(obj))
2614 return convert_dl(obj, tv, pyseq_to_tv, lookupDict);
2615 else if (PyMapping_Check(obj))
2616 return convert_dl(obj, tv, pymap_to_tv, lookupDict);
2617 else
2618 {
2619 PyErr_SetString(PyExc_TypeError, _("unable to convert to vim structure"));
2620 return -1;
2621 }
2622 return 0;
2623}
2624
2625 static PyObject *
2626ConvertToPyObject(typval_T *tv)
2627{
2628 if (tv == NULL)
2629 {
2630 PyErr_SetVim(_("NULL reference passed"));
2631 return NULL;
2632 }
2633 switch (tv->v_type)
2634 {
2635 case VAR_STRING:
2636 return PyBytes_FromString((char *) tv->vval.v_string);
2637 case VAR_NUMBER:
2638 return PyLong_FromLong((long) tv->vval.v_number);
2639#ifdef FEAT_FLOAT
2640 case VAR_FLOAT:
2641 return PyFloat_FromDouble((double) tv->vval.v_float);
2642#endif
2643 case VAR_LIST:
2644 return ListNew(tv->vval.v_list);
2645 case VAR_DICT:
2646 return DictionaryNew(tv->vval.v_dict);
2647 case VAR_FUNC:
2648 return FunctionNew(tv->vval.v_string);
2649 case VAR_UNKNOWN:
2650 Py_INCREF(Py_None);
2651 return Py_None;
2652 default:
2653 PyErr_SetVim(_("internal error: invalid value type"));
2654 return NULL;
2655 }
2656}
2657#endif