##// END OF EJS Templates
parsers: cache the result of index_headrevs...
Bryan O'Sullivan -
r16787:bda96ce9 default
parent child Browse files
Show More
@@ -246,6 +246,7 b' typedef struct {'
246 246 Py_ssize_t raw_length; /* original number of elements */
247 247 Py_ssize_t length; /* current number of elements */
248 248 PyObject *added; /* populated on demand */
249 PyObject *headrevs; /* cache, invalidated on changes */
249 250 nodetree *nt; /* base-16 trie */
250 251 int ntlength; /* # nodes in use */
251 252 int ntcapacity; /* # nodes allocated */
@@ -463,6 +464,7 b' static PyObject *index_insert(indexObjec'
463 464 if (self->nt)
464 465 nt_insert(self, node, (int)offset);
465 466
467 Py_CLEAR(self->headrevs);
466 468 Py_RETURN_NONE;
467 469 }
468 470
@@ -484,6 +486,7 b' static void _index_clearcaches(indexObje'
484 486 free(self->nt);
485 487 self->nt = NULL;
486 488 }
489 Py_CLEAR(self->headrevs);
487 490 }
488 491
489 492 static PyObject *index_clearcaches(indexObject *self)
@@ -534,12 +537,37 b' bail:'
534 537 return NULL;
535 538 }
536 539
540 /*
541 * When we cache a list, we want to be sure the caller can't mutate
542 * the cached copy.
543 */
544 static PyObject *list_copy(PyObject *list)
545 {
546 Py_ssize_t len = PyList_GET_SIZE(list);
547 PyObject *newlist = PyList_New(len);
548 Py_ssize_t i;
549
550 if (newlist == NULL)
551 return NULL;
552
553 for (i = 0; i < len; i++) {
554 PyObject *obj = PyList_GET_ITEM(list, i);
555 Py_INCREF(obj);
556 PyList_SET_ITEM(newlist, i, obj);
557 }
558
559 return newlist;
560 }
561
537 562 static PyObject *index_headrevs(indexObject *self)
538 563 {
539 564 Py_ssize_t i, len, addlen;
540 565 char *nothead = NULL;
541 566 PyObject *heads;
542 567
568 if (self->headrevs)
569 return list_copy(self->headrevs);
570
543 571 len = index_length(self) - 1;
544 572 heads = PyList_New(0);
545 573 if (heads == NULL)
@@ -601,8 +629,9 b' static PyObject *index_headrevs(indexObj'
601 629 }
602 630
603 631 done:
632 self->headrevs = heads;
604 633 free(nothead);
605 return heads;
634 return list_copy(self->headrevs);
606 635 bail:
607 636 Py_XDECREF(heads);
608 637 free(nothead);
@@ -1065,6 +1094,7 b' static int index_slice_del(indexObject *'
1065 1094 ret = PyList_SetSlice(self->added, start - self->length + 1,
1066 1095 PyList_GET_SIZE(self->added), NULL);
1067 1096 done:
1097 Py_CLEAR(self->headrevs);
1068 1098 return ret;
1069 1099 }
1070 1100
@@ -1155,6 +1185,7 b' static int index_init(indexObject *self,'
1155 1185 self->cache = NULL;
1156 1186
1157 1187 self->added = NULL;
1188 self->headrevs = NULL;
1158 1189 self->offsets = NULL;
1159 1190 self->nt = NULL;
1160 1191 self->ntlength = self->ntcapacity = 0;
General Comments 0
You need to be logged in to leave comments. Login now