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