annotate mercurial/cext/manifest.c @ 34438:b90e8da190da

cext: reorder #include We mostly abide by this style. In one case, a blank line was inserted to prevent a local `#include "file"` from coming before a `#include <file>`. Differential Revision: https://phab.mercurial-scm.org/D908
author Gregory Szorc <gregory.szorc@gmail.com>
date Mon, 02 Oct 2017 19:06:00 +0100
parents 0f4ac3b6dee4
children 7ed0750c71a1
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
1 /*
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
2 * manifest.c - manifest type that does on-demand parsing.
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
3 *
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
4 * Copyright 2015, Google Inc.
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
5 *
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
6 * This software may be used and distributed according to the terms of
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
7 * the GNU General Public License, incorporated herein by reference.
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
8 */
24352
d6dbe4d1c9bc manifest: include Python.h before standard headers
Drew Gottlieb <drgott@google.com>
parents: 24312
diff changeset
9 #include <Python.h>
d6dbe4d1c9bc manifest: include Python.h before standard headers
Drew Gottlieb <drgott@google.com>
parents: 24312
diff changeset
10
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
11 #include <assert.h>
34438
b90e8da190da cext: reorder #include
Gregory Szorc <gregory.szorc@gmail.com>
parents: 33758
diff changeset
12 #include <stdlib.h>
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
13 #include <string.h>
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
14
33758
0f4ac3b6dee4 cext: factor out header for charencode.c
Yuya Nishihara <yuya@tcha.org>
parents: 33757
diff changeset
15 #include "charencode.h"
24441
e2ed40f0eb2e manifest: use util.h to get Py_ssize_t
Matt Mackall <mpm@selenic.com>
parents: 24352
diff changeset
16 #include "util.h"
e2ed40f0eb2e manifest: use util.h to get Py_ssize_t
Matt Mackall <mpm@selenic.com>
parents: 24352
diff changeset
17
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
18 #define DEFAULT_LINES 100000
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
19
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
20 typedef struct {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
21 char *start;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
22 Py_ssize_t len; /* length of line including terminal newline */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
23 char hash_suffix;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
24 bool from_malloc;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
25 bool deleted;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
26 } line;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
27
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
28 typedef struct {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
29 PyObject_HEAD
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
30 PyObject *pydata;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
31 line *lines;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
32 int numlines; /* number of line entries */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
33 int livelines; /* number of non-deleted lines */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
34 int maxlines; /* allocated number of lines */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
35 bool dirty;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
36 } lazymanifest;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
37
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
38 #define MANIFEST_OOM -1
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
39 #define MANIFEST_NOT_SORTED -2
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
40 #define MANIFEST_MALFORMED -3
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
41
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
42 /* get the length of the path for a line */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
43 static size_t pathlen(line *l) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
44 return strlen(l->start);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
45 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
46
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
47 /* get the node value of a single line */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
48 static PyObject *nodeof(line *l) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
49 char *s = l->start;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
50 ssize_t llen = pathlen(l);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
51 PyObject *hash = unhexlify(s + llen + 1, 40);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
52 if (!hash) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
53 return NULL;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
54 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
55 if (l->hash_suffix != '\0') {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
56 char newhash[21];
30097
3bf4b762537e manifest: convert PyString* to PyBytes*
Gregory Szorc <gregory.szorc@gmail.com>
parents: 30079
diff changeset
57 memcpy(newhash, PyBytes_AsString(hash), 20);
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
58 Py_DECREF(hash);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
59 newhash[20] = l->hash_suffix;
30097
3bf4b762537e manifest: convert PyString* to PyBytes*
Gregory Szorc <gregory.szorc@gmail.com>
parents: 30079
diff changeset
60 hash = PyBytes_FromStringAndSize(newhash, 21);
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
61 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
62 return hash;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
63 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
64
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
65 /* get the node hash and flags of a line as a tuple */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
66 static PyObject *hashflags(line *l)
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
67 {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
68 char *s = l->start;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
69 size_t plen = pathlen(l);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
70 PyObject *hash = nodeof(l);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
71
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
72 /* 40 for hash, 1 for null byte, 1 for newline */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
73 size_t hplen = plen + 42;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
74 Py_ssize_t flen = l->len - hplen;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
75 PyObject *flags;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
76 PyObject *tup;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
77
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
78 if (!hash)
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
79 return NULL;
30097
3bf4b762537e manifest: convert PyString* to PyBytes*
Gregory Szorc <gregory.szorc@gmail.com>
parents: 30079
diff changeset
80 flags = PyBytes_FromStringAndSize(s + hplen - 1, flen);
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
81 if (!flags) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
82 Py_DECREF(hash);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
83 return NULL;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
84 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
85 tup = PyTuple_Pack(2, hash, flags);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
86 Py_DECREF(flags);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
87 Py_DECREF(hash);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
88 return tup;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
89 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
90
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
91 /* if we're about to run out of space in the line index, add more */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
92 static bool realloc_if_full(lazymanifest *self)
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
93 {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
94 if (self->numlines == self->maxlines) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
95 self->maxlines *= 2;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
96 self->lines = realloc(self->lines, self->maxlines * sizeof(line));
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
97 }
24312
f208ce59a6e5 manifest.c: ensure realloc_if_full() returns 1 or 0
Matt Harbison <matt_harbison@yahoo.com>
parents: 24298
diff changeset
98 return !!self->lines;
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
99 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
100
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
101 /*
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
102 * Find the line boundaries in the manifest that 'data' points to and store
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
103 * information about each line in 'self'.
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
104 */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
105 static int find_lines(lazymanifest *self, char *data, Py_ssize_t len)
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
106 {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
107 char *prev = NULL;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
108 while (len > 0) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
109 line *l;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
110 char *next = memchr(data, '\n', len);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
111 if (!next) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
112 return MANIFEST_MALFORMED;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
113 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
114 next++; /* advance past newline */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
115 if (!realloc_if_full(self)) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
116 return MANIFEST_OOM; /* no memory */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
117 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
118 if (prev && strcmp(prev, data) > -1) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
119 /* This data isn't sorted, so we have to abort. */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
120 return MANIFEST_NOT_SORTED;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
121 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
122 l = self->lines + ((self->numlines)++);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
123 l->start = data;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
124 l->len = next - data;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
125 l->hash_suffix = '\0';
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
126 l->from_malloc = false;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
127 l->deleted = false;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
128 len = len - l->len;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
129 prev = data;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
130 data = next;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
131 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
132 self->livelines = self->numlines;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
133 return 0;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
134 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
135
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
136 static int lazymanifest_init(lazymanifest *self, PyObject *args)
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
137 {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
138 char *data;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
139 Py_ssize_t len;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
140 int err, ret;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
141 PyObject *pydata;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
142 if (!PyArg_ParseTuple(args, "S", &pydata)) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
143 return -1;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
144 }
30097
3bf4b762537e manifest: convert PyString* to PyBytes*
Gregory Szorc <gregory.szorc@gmail.com>
parents: 30079
diff changeset
145 err = PyBytes_AsStringAndSize(pydata, &data, &len);
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
146
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
147 self->dirty = false;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
148 if (err == -1)
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
149 return -1;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
150 self->pydata = pydata;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
151 Py_INCREF(self->pydata);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
152 Py_BEGIN_ALLOW_THREADS
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
153 self->lines = malloc(DEFAULT_LINES * sizeof(line));
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
154 self->maxlines = DEFAULT_LINES;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
155 self->numlines = 0;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
156 if (!self->lines)
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
157 ret = MANIFEST_OOM;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
158 else
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
159 ret = find_lines(self, data, len);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
160 Py_END_ALLOW_THREADS
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
161 switch (ret) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
162 case 0:
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
163 break;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
164 case MANIFEST_OOM:
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
165 PyErr_NoMemory();
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
166 break;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
167 case MANIFEST_NOT_SORTED:
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
168 PyErr_Format(PyExc_ValueError,
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
169 "Manifest lines not in sorted order.");
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
170 break;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
171 case MANIFEST_MALFORMED:
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
172 PyErr_Format(PyExc_ValueError,
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
173 "Manifest did not end in a newline.");
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
174 break;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
175 default:
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
176 PyErr_Format(PyExc_ValueError,
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
177 "Unknown problem parsing manifest.");
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
178 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
179 return ret == 0 ? 0 : -1;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
180 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
181
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
182 static void lazymanifest_dealloc(lazymanifest *self)
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
183 {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
184 /* free any extra lines we had to allocate */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
185 int i;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
186 for (i = 0; i < self->numlines; i++) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
187 if (self->lines[i].from_malloc) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
188 free(self->lines[i].start);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
189 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
190 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
191 if (self->lines) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
192 free(self->lines);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
193 self->lines = NULL;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
194 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
195 if (self->pydata) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
196 Py_DECREF(self->pydata);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
197 self->pydata = NULL;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
198 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
199 PyObject_Del(self);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
200 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
201
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
202 /* iteration support */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
203
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
204 typedef struct {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
205 PyObject_HEAD lazymanifest *m;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
206 Py_ssize_t pos;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
207 } lmIter;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
208
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
209 static void lmiter_dealloc(PyObject *o)
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
210 {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
211 lmIter *self = (lmIter *)o;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
212 Py_DECREF(self->m);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
213 PyObject_Del(self);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
214 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
215
24294
3d485727e45e lazymanifest: extract function for iterating to next line
Martin von Zweigbergk <martinvonz@google.com>
parents: 24293
diff changeset
216 static line *lmiter_nextline(lmIter *self)
3d485727e45e lazymanifest: extract function for iterating to next line
Martin von Zweigbergk <martinvonz@google.com>
parents: 24293
diff changeset
217 {
3d485727e45e lazymanifest: extract function for iterating to next line
Martin von Zweigbergk <martinvonz@google.com>
parents: 24293
diff changeset
218 do {
3d485727e45e lazymanifest: extract function for iterating to next line
Martin von Zweigbergk <martinvonz@google.com>
parents: 24293
diff changeset
219 self->pos++;
3d485727e45e lazymanifest: extract function for iterating to next line
Martin von Zweigbergk <martinvonz@google.com>
parents: 24293
diff changeset
220 if (self->pos >= self->m->numlines) {
3d485727e45e lazymanifest: extract function for iterating to next line
Martin von Zweigbergk <martinvonz@google.com>
parents: 24293
diff changeset
221 return NULL;
3d485727e45e lazymanifest: extract function for iterating to next line
Martin von Zweigbergk <martinvonz@google.com>
parents: 24293
diff changeset
222 }
3d485727e45e lazymanifest: extract function for iterating to next line
Martin von Zweigbergk <martinvonz@google.com>
parents: 24293
diff changeset
223 /* skip over deleted manifest entries */
3d485727e45e lazymanifest: extract function for iterating to next line
Martin von Zweigbergk <martinvonz@google.com>
parents: 24293
diff changeset
224 } while (self->m->lines[self->pos].deleted);
3d485727e45e lazymanifest: extract function for iterating to next line
Martin von Zweigbergk <martinvonz@google.com>
parents: 24293
diff changeset
225 return self->m->lines + self->pos;
3d485727e45e lazymanifest: extract function for iterating to next line
Martin von Zweigbergk <martinvonz@google.com>
parents: 24293
diff changeset
226 }
3d485727e45e lazymanifest: extract function for iterating to next line
Martin von Zweigbergk <martinvonz@google.com>
parents: 24293
diff changeset
227
24298
49cd847fd69a lazymanifest: make __iter__ generate filenames, not 3-tuples
Martin von Zweigbergk <martinvonz@google.com>
parents: 24295
diff changeset
228 static PyObject *lmiter_iterentriesnext(PyObject *o)
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
229 {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
230 size_t pl;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
231 line *l;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
232 Py_ssize_t consumed;
24699
64cd23a1bc13 lazymanifest: fix memory leak in lmiter_iterentriesnext() after 3d485727e45e
Mike Hommey <mh@glandium.org>
parents: 24442
diff changeset
233 PyObject *ret = NULL, *path = NULL, *hash = NULL, *flags = NULL;
24294
3d485727e45e lazymanifest: extract function for iterating to next line
Martin von Zweigbergk <martinvonz@google.com>
parents: 24293
diff changeset
234 l = lmiter_nextline((lmIter *)o);
3d485727e45e lazymanifest: extract function for iterating to next line
Martin von Zweigbergk <martinvonz@google.com>
parents: 24293
diff changeset
235 if (!l) {
24974
46408b80c3a1 lazymanifest: avoid 'bail' label when used on success path
Martin von Zweigbergk <martinvonz@google.com>
parents: 24710
diff changeset
236 goto done;
24294
3d485727e45e lazymanifest: extract function for iterating to next line
Martin von Zweigbergk <martinvonz@google.com>
parents: 24293
diff changeset
237 }
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
238 pl = pathlen(l);
30097
3bf4b762537e manifest: convert PyString* to PyBytes*
Gregory Szorc <gregory.szorc@gmail.com>
parents: 30079
diff changeset
239 path = PyBytes_FromStringAndSize(l->start, pl);
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
240 hash = nodeof(l);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
241 consumed = pl + 41;
30097
3bf4b762537e manifest: convert PyString* to PyBytes*
Gregory Szorc <gregory.szorc@gmail.com>
parents: 30079
diff changeset
242 flags = PyBytes_FromStringAndSize(l->start + consumed,
27340
7b8b6e3b3571 manifest: fix formatting
Bryan O'Sullivan <bos@serpentine.com>
parents: 24975
diff changeset
243 l->len - consumed - 1);
24293
30e9ee203846 lazymanifest: fail if path or hash strings cannot be created
Martin von Zweigbergk <martinvonz@google.com>
parents: 24286
diff changeset
244 if (!path || !hash || !flags) {
24974
46408b80c3a1 lazymanifest: avoid 'bail' label when used on success path
Martin von Zweigbergk <martinvonz@google.com>
parents: 24710
diff changeset
245 goto done;
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
246 }
24699
64cd23a1bc13 lazymanifest: fix memory leak in lmiter_iterentriesnext() after 3d485727e45e
Mike Hommey <mh@glandium.org>
parents: 24442
diff changeset
247 ret = PyTuple_Pack(3, path, hash, flags);
24975
89c2bf63a83b lazymanifest: drop SP before some labels
Martin von Zweigbergk <martinvonz@google.com>
parents: 24974
diff changeset
248 done:
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
249 Py_XDECREF(path);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
250 Py_XDECREF(hash);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
251 Py_XDECREF(flags);
24699
64cd23a1bc13 lazymanifest: fix memory leak in lmiter_iterentriesnext() after 3d485727e45e
Mike Hommey <mh@glandium.org>
parents: 24442
diff changeset
252 return ret;
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
253 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
254
30079
84debea79903 manifest: drop Py_TPFLAGS_HAVE_SEQUENCE_IN from tp_flags in Python 3
Gregory Szorc <gregory.szorc@gmail.com>
parents: 29254
diff changeset
255 #ifdef IS_PY3K
84debea79903 manifest: drop Py_TPFLAGS_HAVE_SEQUENCE_IN from tp_flags in Python 3
Gregory Szorc <gregory.szorc@gmail.com>
parents: 29254
diff changeset
256 #define LAZYMANIFESTENTRIESITERATOR_TPFLAGS Py_TPFLAGS_DEFAULT
84debea79903 manifest: drop Py_TPFLAGS_HAVE_SEQUENCE_IN from tp_flags in Python 3
Gregory Szorc <gregory.szorc@gmail.com>
parents: 29254
diff changeset
257 #else
84debea79903 manifest: drop Py_TPFLAGS_HAVE_SEQUENCE_IN from tp_flags in Python 3
Gregory Szorc <gregory.szorc@gmail.com>
parents: 29254
diff changeset
258 #define LAZYMANIFESTENTRIESITERATOR_TPFLAGS Py_TPFLAGS_DEFAULT \
84debea79903 manifest: drop Py_TPFLAGS_HAVE_SEQUENCE_IN from tp_flags in Python 3
Gregory Szorc <gregory.szorc@gmail.com>
parents: 29254
diff changeset
259 | Py_TPFLAGS_HAVE_ITER
84debea79903 manifest: drop Py_TPFLAGS_HAVE_SEQUENCE_IN from tp_flags in Python 3
Gregory Szorc <gregory.szorc@gmail.com>
parents: 29254
diff changeset
260 #endif
84debea79903 manifest: drop Py_TPFLAGS_HAVE_SEQUENCE_IN from tp_flags in Python 3
Gregory Szorc <gregory.szorc@gmail.com>
parents: 29254
diff changeset
261
24298
49cd847fd69a lazymanifest: make __iter__ generate filenames, not 3-tuples
Martin von Zweigbergk <martinvonz@google.com>
parents: 24295
diff changeset
262 static PyTypeObject lazymanifestEntriesIterator = {
30168
1a327889c13c manifest: use PyVarObject_HEAD_INIT
Gregory Szorc <gregory.szorc@gmail.com>
parents: 30097
diff changeset
263 PyVarObject_HEAD_INIT(NULL, 0)
24298
49cd847fd69a lazymanifest: make __iter__ generate filenames, not 3-tuples
Martin von Zweigbergk <martinvonz@google.com>
parents: 24295
diff changeset
264 "parsers.lazymanifest.entriesiterator", /*tp_name */
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
265 sizeof(lmIter), /*tp_basicsize */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
266 0, /*tp_itemsize */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
267 lmiter_dealloc, /*tp_dealloc */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
268 0, /*tp_print */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
269 0, /*tp_getattr */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
270 0, /*tp_setattr */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
271 0, /*tp_compare */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
272 0, /*tp_repr */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
273 0, /*tp_as_number */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
274 0, /*tp_as_sequence */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
275 0, /*tp_as_mapping */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
276 0, /*tp_hash */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
277 0, /*tp_call */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
278 0, /*tp_str */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
279 0, /*tp_getattro */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
280 0, /*tp_setattro */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
281 0, /*tp_as_buffer */
30079
84debea79903 manifest: drop Py_TPFLAGS_HAVE_SEQUENCE_IN from tp_flags in Python 3
Gregory Szorc <gregory.szorc@gmail.com>
parents: 29254
diff changeset
282 LAZYMANIFESTENTRIESITERATOR_TPFLAGS, /* tp_flags */
24298
49cd847fd69a lazymanifest: make __iter__ generate filenames, not 3-tuples
Martin von Zweigbergk <martinvonz@google.com>
parents: 24295
diff changeset
283 "Iterator for 3-tuples in a lazymanifest.", /* tp_doc */
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
284 0, /* tp_traverse */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
285 0, /* tp_clear */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
286 0, /* tp_richcompare */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
287 0, /* tp_weaklistoffset */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
288 PyObject_SelfIter, /* tp_iter: __iter__() method */
24298
49cd847fd69a lazymanifest: make __iter__ generate filenames, not 3-tuples
Martin von Zweigbergk <martinvonz@google.com>
parents: 24295
diff changeset
289 lmiter_iterentriesnext, /* tp_iternext: next() method */
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
290 };
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
291
24295
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
292 static PyObject *lmiter_iterkeysnext(PyObject *o)
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
293 {
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
294 size_t pl;
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
295 line *l = lmiter_nextline((lmIter *)o);
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
296 if (!l) {
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
297 return NULL;
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
298 }
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
299 pl = pathlen(l);
30097
3bf4b762537e manifest: convert PyString* to PyBytes*
Gregory Szorc <gregory.szorc@gmail.com>
parents: 30079
diff changeset
300 return PyBytes_FromStringAndSize(l->start, pl);
24295
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
301 }
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
302
30079
84debea79903 manifest: drop Py_TPFLAGS_HAVE_SEQUENCE_IN from tp_flags in Python 3
Gregory Szorc <gregory.szorc@gmail.com>
parents: 29254
diff changeset
303 #ifdef IS_PY3K
84debea79903 manifest: drop Py_TPFLAGS_HAVE_SEQUENCE_IN from tp_flags in Python 3
Gregory Szorc <gregory.szorc@gmail.com>
parents: 29254
diff changeset
304 #define LAZYMANIFESTKEYSITERATOR_TPFLAGS Py_TPFLAGS_DEFAULT
84debea79903 manifest: drop Py_TPFLAGS_HAVE_SEQUENCE_IN from tp_flags in Python 3
Gregory Szorc <gregory.szorc@gmail.com>
parents: 29254
diff changeset
305 #else
84debea79903 manifest: drop Py_TPFLAGS_HAVE_SEQUENCE_IN from tp_flags in Python 3
Gregory Szorc <gregory.szorc@gmail.com>
parents: 29254
diff changeset
306 #define LAZYMANIFESTKEYSITERATOR_TPFLAGS Py_TPFLAGS_DEFAULT \
84debea79903 manifest: drop Py_TPFLAGS_HAVE_SEQUENCE_IN from tp_flags in Python 3
Gregory Szorc <gregory.szorc@gmail.com>
parents: 29254
diff changeset
307 | Py_TPFLAGS_HAVE_ITER
84debea79903 manifest: drop Py_TPFLAGS_HAVE_SEQUENCE_IN from tp_flags in Python 3
Gregory Szorc <gregory.szorc@gmail.com>
parents: 29254
diff changeset
308 #endif
84debea79903 manifest: drop Py_TPFLAGS_HAVE_SEQUENCE_IN from tp_flags in Python 3
Gregory Szorc <gregory.szorc@gmail.com>
parents: 29254
diff changeset
309
24295
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
310 static PyTypeObject lazymanifestKeysIterator = {
30168
1a327889c13c manifest: use PyVarObject_HEAD_INIT
Gregory Szorc <gregory.szorc@gmail.com>
parents: 30097
diff changeset
311 PyVarObject_HEAD_INIT(NULL, 0)
24295
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
312 "parsers.lazymanifest.keysiterator", /*tp_name */
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
313 sizeof(lmIter), /*tp_basicsize */
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
314 0, /*tp_itemsize */
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
315 lmiter_dealloc, /*tp_dealloc */
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
316 0, /*tp_print */
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
317 0, /*tp_getattr */
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
318 0, /*tp_setattr */
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
319 0, /*tp_compare */
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
320 0, /*tp_repr */
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
321 0, /*tp_as_number */
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
322 0, /*tp_as_sequence */
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
323 0, /*tp_as_mapping */
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
324 0, /*tp_hash */
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
325 0, /*tp_call */
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
326 0, /*tp_str */
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
327 0, /*tp_getattro */
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
328 0, /*tp_setattro */
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
329 0, /*tp_as_buffer */
30079
84debea79903 manifest: drop Py_TPFLAGS_HAVE_SEQUENCE_IN from tp_flags in Python 3
Gregory Szorc <gregory.szorc@gmail.com>
parents: 29254
diff changeset
330 LAZYMANIFESTKEYSITERATOR_TPFLAGS, /* tp_flags */
24295
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
331 "Keys iterator for a lazymanifest.", /* tp_doc */
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
332 0, /* tp_traverse */
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
333 0, /* tp_clear */
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
334 0, /* tp_richcompare */
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
335 0, /* tp_weaklistoffset */
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
336 PyObject_SelfIter, /* tp_iter: __iter__() method */
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
337 lmiter_iterkeysnext, /* tp_iternext: next() method */
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
338 };
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
339
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
340 static lazymanifest *lazymanifest_copy(lazymanifest *self);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
341
24298
49cd847fd69a lazymanifest: make __iter__ generate filenames, not 3-tuples
Martin von Zweigbergk <martinvonz@google.com>
parents: 24295
diff changeset
342 static PyObject *lazymanifest_getentriesiter(lazymanifest *self)
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
343 {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
344 lmIter *i = NULL;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
345 lazymanifest *t = lazymanifest_copy(self);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
346 if (!t) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
347 PyErr_NoMemory();
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
348 return NULL;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
349 }
24298
49cd847fd69a lazymanifest: make __iter__ generate filenames, not 3-tuples
Martin von Zweigbergk <martinvonz@google.com>
parents: 24295
diff changeset
350 i = PyObject_New(lmIter, &lazymanifestEntriesIterator);
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
351 if (i) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
352 i->m = t;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
353 i->pos = -1;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
354 } else {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
355 Py_DECREF(t);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
356 PyErr_NoMemory();
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
357 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
358 return (PyObject *)i;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
359 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
360
24295
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
361 static PyObject *lazymanifest_getkeysiter(lazymanifest *self)
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
362 {
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
363 lmIter *i = NULL;
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
364 lazymanifest *t = lazymanifest_copy(self);
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
365 if (!t) {
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
366 PyErr_NoMemory();
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
367 return NULL;
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
368 }
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
369 i = PyObject_New(lmIter, &lazymanifestKeysIterator);
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
370 if (i) {
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
371 i->m = t;
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
372 i->pos = -1;
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
373 } else {
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
374 Py_DECREF(t);
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
375 PyErr_NoMemory();
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
376 }
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
377 return (PyObject *)i;
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
378 }
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
379
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
380 /* __getitem__ and __setitem__ support */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
381
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
382 static Py_ssize_t lazymanifest_size(lazymanifest *self)
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
383 {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
384 return self->livelines;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
385 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
386
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
387 static int linecmp(const void *left, const void *right)
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
388 {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
389 return strcmp(((const line *)left)->start,
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
390 ((const line *)right)->start);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
391 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
392
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
393 static PyObject *lazymanifest_getitem(lazymanifest *self, PyObject *key)
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
394 {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
395 line needle;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
396 line *hit;
30097
3bf4b762537e manifest: convert PyString* to PyBytes*
Gregory Szorc <gregory.szorc@gmail.com>
parents: 30079
diff changeset
397 if (!PyBytes_Check(key)) {
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
398 PyErr_Format(PyExc_TypeError,
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
399 "getitem: manifest keys must be a string.");
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
400 return NULL;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
401 }
30097
3bf4b762537e manifest: convert PyString* to PyBytes*
Gregory Szorc <gregory.szorc@gmail.com>
parents: 30079
diff changeset
402 needle.start = PyBytes_AsString(key);
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
403 hit = bsearch(&needle, self->lines, self->numlines, sizeof(line),
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
404 &linecmp);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
405 if (!hit || hit->deleted) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
406 PyErr_Format(PyExc_KeyError, "No such manifest entry.");
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
407 return NULL;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
408 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
409 return hashflags(hit);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
410 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
411
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
412 static int lazymanifest_delitem(lazymanifest *self, PyObject *key)
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
413 {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
414 line needle;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
415 line *hit;
30097
3bf4b762537e manifest: convert PyString* to PyBytes*
Gregory Szorc <gregory.szorc@gmail.com>
parents: 30079
diff changeset
416 if (!PyBytes_Check(key)) {
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
417 PyErr_Format(PyExc_TypeError,
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
418 "delitem: manifest keys must be a string.");
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
419 return -1;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
420 }
30097
3bf4b762537e manifest: convert PyString* to PyBytes*
Gregory Szorc <gregory.szorc@gmail.com>
parents: 30079
diff changeset
421 needle.start = PyBytes_AsString(key);
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
422 hit = bsearch(&needle, self->lines, self->numlines, sizeof(line),
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
423 &linecmp);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
424 if (!hit || hit->deleted) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
425 PyErr_Format(PyExc_KeyError,
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
426 "Tried to delete nonexistent manifest entry.");
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
427 return -1;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
428 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
429 self->dirty = true;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
430 hit->deleted = true;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
431 self->livelines--;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
432 return 0;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
433 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
434
24228
542c891274b2 lazymanifest: use a binary search to do an insertion
Augie Fackler <augie@google.com>
parents: 24214
diff changeset
435 /* Do a binary search for the insertion point for new, creating the
542c891274b2 lazymanifest: use a binary search to do an insertion
Augie Fackler <augie@google.com>
parents: 24214
diff changeset
436 * new entry if needed. */
542c891274b2 lazymanifest: use a binary search to do an insertion
Augie Fackler <augie@google.com>
parents: 24214
diff changeset
437 static int internalsetitem(lazymanifest *self, line *new) {
542c891274b2 lazymanifest: use a binary search to do an insertion
Augie Fackler <augie@google.com>
parents: 24214
diff changeset
438 int start = 0, end = self->numlines;
542c891274b2 lazymanifest: use a binary search to do an insertion
Augie Fackler <augie@google.com>
parents: 24214
diff changeset
439 while (start < end) {
542c891274b2 lazymanifest: use a binary search to do an insertion
Augie Fackler <augie@google.com>
parents: 24214
diff changeset
440 int pos = start + (end - start) / 2;
542c891274b2 lazymanifest: use a binary search to do an insertion
Augie Fackler <augie@google.com>
parents: 24214
diff changeset
441 int c = linecmp(new, self->lines + pos);
542c891274b2 lazymanifest: use a binary search to do an insertion
Augie Fackler <augie@google.com>
parents: 24214
diff changeset
442 if (c < 0)
542c891274b2 lazymanifest: use a binary search to do an insertion
Augie Fackler <augie@google.com>
parents: 24214
diff changeset
443 end = pos;
542c891274b2 lazymanifest: use a binary search to do an insertion
Augie Fackler <augie@google.com>
parents: 24214
diff changeset
444 else if (c > 0)
542c891274b2 lazymanifest: use a binary search to do an insertion
Augie Fackler <augie@google.com>
parents: 24214
diff changeset
445 start = pos + 1;
542c891274b2 lazymanifest: use a binary search to do an insertion
Augie Fackler <augie@google.com>
parents: 24214
diff changeset
446 else {
542c891274b2 lazymanifest: use a binary search to do an insertion
Augie Fackler <augie@google.com>
parents: 24214
diff changeset
447 if (self->lines[pos].deleted)
542c891274b2 lazymanifest: use a binary search to do an insertion
Augie Fackler <augie@google.com>
parents: 24214
diff changeset
448 self->livelines++;
24710
909ee6b2a024 lazymanifest: prevent leak when updating an entry more than once
Augie Fackler <augie@google.com>
parents: 24699
diff changeset
449 if (self->lines[pos].from_malloc)
909ee6b2a024 lazymanifest: prevent leak when updating an entry more than once
Augie Fackler <augie@google.com>
parents: 24699
diff changeset
450 free(self->lines[pos].start);
24228
542c891274b2 lazymanifest: use a binary search to do an insertion
Augie Fackler <augie@google.com>
parents: 24214
diff changeset
451 start = pos;
542c891274b2 lazymanifest: use a binary search to do an insertion
Augie Fackler <augie@google.com>
parents: 24214
diff changeset
452 goto finish;
542c891274b2 lazymanifest: use a binary search to do an insertion
Augie Fackler <augie@google.com>
parents: 24214
diff changeset
453 }
542c891274b2 lazymanifest: use a binary search to do an insertion
Augie Fackler <augie@google.com>
parents: 24214
diff changeset
454 }
542c891274b2 lazymanifest: use a binary search to do an insertion
Augie Fackler <augie@google.com>
parents: 24214
diff changeset
455 /* being here means we need to do an insert */
542c891274b2 lazymanifest: use a binary search to do an insertion
Augie Fackler <augie@google.com>
parents: 24214
diff changeset
456 if (!realloc_if_full(self)) {
542c891274b2 lazymanifest: use a binary search to do an insertion
Augie Fackler <augie@google.com>
parents: 24214
diff changeset
457 PyErr_NoMemory();
542c891274b2 lazymanifest: use a binary search to do an insertion
Augie Fackler <augie@google.com>
parents: 24214
diff changeset
458 return -1;
542c891274b2 lazymanifest: use a binary search to do an insertion
Augie Fackler <augie@google.com>
parents: 24214
diff changeset
459 }
542c891274b2 lazymanifest: use a binary search to do an insertion
Augie Fackler <augie@google.com>
parents: 24214
diff changeset
460 memmove(self->lines + start + 1, self->lines + start,
542c891274b2 lazymanifest: use a binary search to do an insertion
Augie Fackler <augie@google.com>
parents: 24214
diff changeset
461 (self->numlines - start) * sizeof(line));
542c891274b2 lazymanifest: use a binary search to do an insertion
Augie Fackler <augie@google.com>
parents: 24214
diff changeset
462 self->numlines++;
542c891274b2 lazymanifest: use a binary search to do an insertion
Augie Fackler <augie@google.com>
parents: 24214
diff changeset
463 self->livelines++;
542c891274b2 lazymanifest: use a binary search to do an insertion
Augie Fackler <augie@google.com>
parents: 24214
diff changeset
464 finish:
542c891274b2 lazymanifest: use a binary search to do an insertion
Augie Fackler <augie@google.com>
parents: 24214
diff changeset
465 self->lines[start] = *new;
542c891274b2 lazymanifest: use a binary search to do an insertion
Augie Fackler <augie@google.com>
parents: 24214
diff changeset
466 self->dirty = true;
542c891274b2 lazymanifest: use a binary search to do an insertion
Augie Fackler <augie@google.com>
parents: 24214
diff changeset
467 return 0;
542c891274b2 lazymanifest: use a binary search to do an insertion
Augie Fackler <augie@google.com>
parents: 24214
diff changeset
468 }
542c891274b2 lazymanifest: use a binary search to do an insertion
Augie Fackler <augie@google.com>
parents: 24214
diff changeset
469
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
470 static int lazymanifest_setitem(
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
471 lazymanifest *self, PyObject *key, PyObject *value)
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
472 {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
473 char *path;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
474 Py_ssize_t plen;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
475 PyObject *pyhash;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
476 Py_ssize_t hlen;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
477 char *hash;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
478 PyObject *pyflags;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
479 char *flags;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
480 Py_ssize_t flen;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
481 size_t dlen;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
482 char *dest;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
483 int i;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
484 line new;
30097
3bf4b762537e manifest: convert PyString* to PyBytes*
Gregory Szorc <gregory.szorc@gmail.com>
parents: 30079
diff changeset
485 if (!PyBytes_Check(key)) {
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
486 PyErr_Format(PyExc_TypeError,
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
487 "setitem: manifest keys must be a string.");
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
488 return -1;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
489 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
490 if (!value) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
491 return lazymanifest_delitem(self, key);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
492 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
493 if (!PyTuple_Check(value) || PyTuple_Size(value) != 2) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
494 PyErr_Format(PyExc_TypeError,
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
495 "Manifest values must be a tuple of (node, flags).");
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
496 return -1;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
497 }
30097
3bf4b762537e manifest: convert PyString* to PyBytes*
Gregory Szorc <gregory.szorc@gmail.com>
parents: 30079
diff changeset
498 if (PyBytes_AsStringAndSize(key, &path, &plen) == -1) {
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
499 return -1;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
500 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
501
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
502 pyhash = PyTuple_GetItem(value, 0);
30097
3bf4b762537e manifest: convert PyString* to PyBytes*
Gregory Szorc <gregory.szorc@gmail.com>
parents: 30079
diff changeset
503 if (!PyBytes_Check(pyhash)) {
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
504 PyErr_Format(PyExc_TypeError,
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
505 "node must be a 20-byte string");
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
506 return -1;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
507 }
30097
3bf4b762537e manifest: convert PyString* to PyBytes*
Gregory Szorc <gregory.szorc@gmail.com>
parents: 30079
diff changeset
508 hlen = PyBytes_Size(pyhash);
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
509 /* Some parts of the codebase try and set 21 or 22
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
510 * byte "hash" values in order to perturb things for
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
511 * status. We have to preserve at least the 21st
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
512 * byte. Sigh. If there's a 22nd byte, we drop it on
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
513 * the floor, which works fine.
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
514 */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
515 if (hlen != 20 && hlen != 21 && hlen != 22) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
516 PyErr_Format(PyExc_TypeError,
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
517 "node must be a 20-byte string");
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
518 return -1;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
519 }
30097
3bf4b762537e manifest: convert PyString* to PyBytes*
Gregory Szorc <gregory.szorc@gmail.com>
parents: 30079
diff changeset
520 hash = PyBytes_AsString(pyhash);
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
521
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
522 pyflags = PyTuple_GetItem(value, 1);
30097
3bf4b762537e manifest: convert PyString* to PyBytes*
Gregory Szorc <gregory.szorc@gmail.com>
parents: 30079
diff changeset
523 if (!PyBytes_Check(pyflags) || PyBytes_Size(pyflags) > 1) {
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
524 PyErr_Format(PyExc_TypeError,
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
525 "flags must a 0 or 1 byte string");
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
526 return -1;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
527 }
30097
3bf4b762537e manifest: convert PyString* to PyBytes*
Gregory Szorc <gregory.szorc@gmail.com>
parents: 30079
diff changeset
528 if (PyBytes_AsStringAndSize(pyflags, &flags, &flen) == -1) {
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
529 return -1;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
530 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
531 /* one null byte and one newline */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
532 dlen = plen + 41 + flen + 1;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
533 dest = malloc(dlen);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
534 if (!dest) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
535 PyErr_NoMemory();
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
536 return -1;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
537 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
538 memcpy(dest, path, plen + 1);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
539 for (i = 0; i < 20; i++) {
24286
40528ad1b1e8 lazymanifest: don't depend on printf's 'hh' format to work
Martin von Zweigbergk <martinvonz@google.com>
parents: 24228
diff changeset
540 /* Cast to unsigned, so it will not get sign-extended when promoted
40528ad1b1e8 lazymanifest: don't depend on printf's 'hh' format to work
Martin von Zweigbergk <martinvonz@google.com>
parents: 24228
diff changeset
541 * to int (as is done when passing to a variadic function)
40528ad1b1e8 lazymanifest: don't depend on printf's 'hh' format to work
Martin von Zweigbergk <martinvonz@google.com>
parents: 24228
diff changeset
542 */
40528ad1b1e8 lazymanifest: don't depend on printf's 'hh' format to work
Martin von Zweigbergk <martinvonz@google.com>
parents: 24228
diff changeset
543 sprintf(dest + plen + 1 + (i * 2), "%02x", (unsigned char)hash[i]);
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
544 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
545 memcpy(dest + plen + 41, flags, flen);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
546 dest[plen + 41 + flen] = '\n';
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
547 new.start = dest;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
548 new.len = dlen;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
549 new.hash_suffix = '\0';
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
550 if (hlen > 20) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
551 new.hash_suffix = hash[20];
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
552 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
553 new.from_malloc = true; /* is `start` a pointer we allocated? */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
554 new.deleted = false; /* is this entry deleted? */
24228
542c891274b2 lazymanifest: use a binary search to do an insertion
Augie Fackler <augie@google.com>
parents: 24214
diff changeset
555 if (internalsetitem(self, &new)) {
542c891274b2 lazymanifest: use a binary search to do an insertion
Augie Fackler <augie@google.com>
parents: 24214
diff changeset
556 return -1;
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
557 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
558 return 0;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
559 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
560
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
561 static PyMappingMethods lazymanifest_mapping_methods = {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
562 (lenfunc)lazymanifest_size, /* mp_length */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
563 (binaryfunc)lazymanifest_getitem, /* mp_subscript */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
564 (objobjargproc)lazymanifest_setitem, /* mp_ass_subscript */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
565 };
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
566
27608
d6aa1a8c8d7c lazymanifest: add missing closing parenthesis in comment
Augie Fackler <raf@durin42.com>
parents: 27340
diff changeset
567 /* sequence methods (important or __contains__ builds an iterator) */
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
568
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
569 static int lazymanifest_contains(lazymanifest *self, PyObject *key)
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
570 {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
571 line needle;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
572 line *hit;
30097
3bf4b762537e manifest: convert PyString* to PyBytes*
Gregory Szorc <gregory.szorc@gmail.com>
parents: 30079
diff changeset
573 if (!PyBytes_Check(key)) {
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
574 /* Our keys are always strings, so if the contains
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
575 * check is for a non-string, just return false. */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
576 return 0;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
577 }
30097
3bf4b762537e manifest: convert PyString* to PyBytes*
Gregory Szorc <gregory.szorc@gmail.com>
parents: 30079
diff changeset
578 needle.start = PyBytes_AsString(key);
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
579 hit = bsearch(&needle, self->lines, self->numlines, sizeof(line),
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
580 &linecmp);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
581 if (!hit || hit->deleted) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
582 return 0;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
583 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
584 return 1;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
585 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
586
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
587 static PySequenceMethods lazymanifest_seq_meths = {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
588 (lenfunc)lazymanifest_size, /* sq_length */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
589 0, /* sq_concat */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
590 0, /* sq_repeat */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
591 0, /* sq_item */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
592 0, /* sq_slice */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
593 0, /* sq_ass_item */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
594 0, /* sq_ass_slice */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
595 (objobjproc)lazymanifest_contains, /* sq_contains */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
596 0, /* sq_inplace_concat */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
597 0, /* sq_inplace_repeat */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
598 };
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
599
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
600
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
601 /* Other methods (copy, diff, etc) */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
602 static PyTypeObject lazymanifestType;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
603
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
604 /* If the manifest has changes, build the new manifest text and reindex it. */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
605 static int compact(lazymanifest *self) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
606 int i;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
607 ssize_t need = 0;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
608 char *data;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
609 line *src, *dst;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
610 PyObject *pydata;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
611 if (!self->dirty)
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
612 return 0;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
613 for (i = 0; i < self->numlines; i++) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
614 if (!self->lines[i].deleted) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
615 need += self->lines[i].len;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
616 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
617 }
30097
3bf4b762537e manifest: convert PyString* to PyBytes*
Gregory Szorc <gregory.szorc@gmail.com>
parents: 30079
diff changeset
618 pydata = PyBytes_FromStringAndSize(NULL, need);
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
619 if (!pydata)
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
620 return -1;
30097
3bf4b762537e manifest: convert PyString* to PyBytes*
Gregory Szorc <gregory.szorc@gmail.com>
parents: 30079
diff changeset
621 data = PyBytes_AsString(pydata);
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
622 if (!data) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
623 return -1;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
624 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
625 src = self->lines;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
626 dst = self->lines;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
627 for (i = 0; i < self->numlines; i++, src++) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
628 char *tofree = NULL;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
629 if (src->from_malloc) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
630 tofree = src->start;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
631 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
632 if (!src->deleted) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
633 memcpy(data, src->start, src->len);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
634 *dst = *src;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
635 dst->start = data;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
636 dst->from_malloc = false;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
637 data += dst->len;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
638 dst++;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
639 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
640 free(tofree);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
641 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
642 Py_DECREF(self->pydata);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
643 self->pydata = pydata;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
644 self->numlines = self->livelines;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
645 self->dirty = false;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
646 return 0;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
647 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
648
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
649 static PyObject *lazymanifest_text(lazymanifest *self)
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
650 {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
651 if (compact(self) != 0) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
652 PyErr_NoMemory();
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
653 return NULL;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
654 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
655 Py_INCREF(self->pydata);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
656 return self->pydata;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
657 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
658
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
659 static lazymanifest *lazymanifest_copy(lazymanifest *self)
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
660 {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
661 lazymanifest *copy = NULL;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
662 if (compact(self) != 0) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
663 goto nomem;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
664 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
665 copy = PyObject_New(lazymanifest, &lazymanifestType);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
666 if (!copy) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
667 goto nomem;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
668 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
669 copy->numlines = self->numlines;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
670 copy->livelines = self->livelines;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
671 copy->dirty = false;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
672 copy->lines = malloc(self->maxlines *sizeof(line));
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
673 if (!copy->lines) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
674 goto nomem;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
675 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
676 memcpy(copy->lines, self->lines, self->numlines * sizeof(line));
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
677 copy->maxlines = self->maxlines;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
678 copy->pydata = self->pydata;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
679 Py_INCREF(copy->pydata);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
680 return copy;
24975
89c2bf63a83b lazymanifest: drop SP before some labels
Martin von Zweigbergk <martinvonz@google.com>
parents: 24974
diff changeset
681 nomem:
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
682 PyErr_NoMemory();
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
683 Py_XDECREF(copy);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
684 return NULL;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
685 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
686
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
687 static lazymanifest *lazymanifest_filtercopy(
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
688 lazymanifest *self, PyObject *matchfn)
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
689 {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
690 lazymanifest *copy = NULL;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
691 int i;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
692 if (!PyCallable_Check(matchfn)) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
693 PyErr_SetString(PyExc_TypeError, "matchfn must be callable");
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
694 return NULL;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
695 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
696 /* compact ourselves first to avoid double-frees later when we
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
697 * compact tmp so that it doesn't have random pointers to our
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
698 * underlying from_malloc-data (self->pydata is safe) */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
699 if (compact(self) != 0) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
700 goto nomem;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
701 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
702 copy = PyObject_New(lazymanifest, &lazymanifestType);
27609
ca2d4080a02e lazymanifest: check error return in filter
Augie Fackler <raf@durin42.com>
parents: 27608
diff changeset
703 if (!copy) {
ca2d4080a02e lazymanifest: check error return in filter
Augie Fackler <raf@durin42.com>
parents: 27608
diff changeset
704 goto nomem;
ca2d4080a02e lazymanifest: check error return in filter
Augie Fackler <raf@durin42.com>
parents: 27608
diff changeset
705 }
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
706 copy->dirty = true;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
707 copy->lines = malloc(self->maxlines * sizeof(line));
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
708 if (!copy->lines) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
709 goto nomem;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
710 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
711 copy->maxlines = self->maxlines;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
712 copy->numlines = 0;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
713 copy->pydata = self->pydata;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
714 Py_INCREF(self->pydata);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
715 for (i = 0; i < self->numlines; i++) {
27661
abc79f44f548 lazymanifest: check more return values in filtercopy
Augie Fackler <raf@durin42.com>
parents: 27609
diff changeset
716 PyObject *arglist = NULL, *result = NULL;
abc79f44f548 lazymanifest: check more return values in filtercopy
Augie Fackler <raf@durin42.com>
parents: 27609
diff changeset
717 arglist = Py_BuildValue("(s)", self->lines[i].start);
abc79f44f548 lazymanifest: check more return values in filtercopy
Augie Fackler <raf@durin42.com>
parents: 27609
diff changeset
718 if (!arglist) {
abc79f44f548 lazymanifest: check more return values in filtercopy
Augie Fackler <raf@durin42.com>
parents: 27609
diff changeset
719 return NULL;
abc79f44f548 lazymanifest: check more return values in filtercopy
Augie Fackler <raf@durin42.com>
parents: 27609
diff changeset
720 }
abc79f44f548 lazymanifest: check more return values in filtercopy
Augie Fackler <raf@durin42.com>
parents: 27609
diff changeset
721 result = PyObject_CallObject(matchfn, arglist);
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
722 Py_DECREF(arglist);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
723 /* if the callback raised an exception, just let it
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
724 * through and give up */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
725 if (!result) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
726 free(copy->lines);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
727 Py_DECREF(self->pydata);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
728 return NULL;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
729 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
730 if (PyObject_IsTrue(result)) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
731 assert(!(self->lines[i].from_malloc));
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
732 copy->lines[copy->numlines++] = self->lines[i];
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
733 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
734 Py_DECREF(result);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
735 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
736 copy->livelines = copy->numlines;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
737 return copy;
24975
89c2bf63a83b lazymanifest: drop SP before some labels
Martin von Zweigbergk <martinvonz@google.com>
parents: 24974
diff changeset
738 nomem:
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
739 PyErr_NoMemory();
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
740 Py_XDECREF(copy);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
741 return NULL;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
742 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
743
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
744 static PyObject *lazymanifest_diff(lazymanifest *self, PyObject *args)
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
745 {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
746 lazymanifest *other;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
747 PyObject *pyclean = NULL;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
748 bool listclean;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
749 PyObject *emptyTup = NULL, *ret = NULL;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
750 PyObject *es;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
751 int sneedle = 0, oneedle = 0;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
752 if (!PyArg_ParseTuple(args, "O!|O", &lazymanifestType, &other, &pyclean)) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
753 return NULL;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
754 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
755 listclean = (!pyclean) ? false : PyObject_IsTrue(pyclean);
30097
3bf4b762537e manifest: convert PyString* to PyBytes*
Gregory Szorc <gregory.szorc@gmail.com>
parents: 30079
diff changeset
756 es = PyBytes_FromString("");
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
757 if (!es) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
758 goto nomem;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
759 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
760 emptyTup = PyTuple_Pack(2, Py_None, es);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
761 Py_DECREF(es);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
762 if (!emptyTup) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
763 goto nomem;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
764 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
765 ret = PyDict_New();
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
766 if (!ret) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
767 goto nomem;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
768 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
769 while (sneedle != self->numlines || oneedle != other->numlines) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
770 line *left = self->lines + sneedle;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
771 line *right = other->lines + oneedle;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
772 int result;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
773 PyObject *key;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
774 PyObject *outer;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
775 /* If we're looking at a deleted entry and it's not
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
776 * the end of the manifest, just skip it. */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
777 if (left->deleted && sneedle < self->numlines) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
778 sneedle++;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
779 continue;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
780 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
781 if (right->deleted && oneedle < other->numlines) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
782 oneedle++;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
783 continue;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
784 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
785 /* if we're at the end of either manifest, then we
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
786 * know the remaining items are adds so we can skip
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
787 * the strcmp. */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
788 if (sneedle == self->numlines) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
789 result = 1;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
790 } else if (oneedle == other->numlines) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
791 result = -1;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
792 } else {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
793 result = linecmp(left, right);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
794 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
795 key = result <= 0 ?
30097
3bf4b762537e manifest: convert PyString* to PyBytes*
Gregory Szorc <gregory.szorc@gmail.com>
parents: 30079
diff changeset
796 PyBytes_FromString(left->start) :
3bf4b762537e manifest: convert PyString* to PyBytes*
Gregory Szorc <gregory.szorc@gmail.com>
parents: 30079
diff changeset
797 PyBytes_FromString(right->start);
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
798 if (!key)
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
799 goto nomem;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
800 if (result < 0) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
801 PyObject *l = hashflags(left);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
802 if (!l) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
803 goto nomem;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
804 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
805 outer = PyTuple_Pack(2, l, emptyTup);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
806 Py_DECREF(l);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
807 if (!outer) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
808 goto nomem;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
809 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
810 PyDict_SetItem(ret, key, outer);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
811 Py_DECREF(outer);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
812 sneedle++;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
813 } else if (result > 0) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
814 PyObject *r = hashflags(right);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
815 if (!r) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
816 goto nomem;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
817 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
818 outer = PyTuple_Pack(2, emptyTup, r);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
819 Py_DECREF(r);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
820 if (!outer) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
821 goto nomem;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
822 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
823 PyDict_SetItem(ret, key, outer);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
824 Py_DECREF(outer);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
825 oneedle++;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
826 } else {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
827 /* file exists in both manifests */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
828 if (left->len != right->len
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
829 || memcmp(left->start, right->start, left->len)
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
830 || left->hash_suffix != right->hash_suffix) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
831 PyObject *l = hashflags(left);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
832 PyObject *r;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
833 if (!l) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
834 goto nomem;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
835 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
836 r = hashflags(right);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
837 if (!r) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
838 Py_DECREF(l);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
839 goto nomem;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
840 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
841 outer = PyTuple_Pack(2, l, r);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
842 Py_DECREF(l);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
843 Py_DECREF(r);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
844 if (!outer) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
845 goto nomem;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
846 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
847 PyDict_SetItem(ret, key, outer);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
848 Py_DECREF(outer);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
849 } else if (listclean) {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
850 PyDict_SetItem(ret, key, Py_None);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
851 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
852 sneedle++;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
853 oneedle++;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
854 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
855 Py_DECREF(key);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
856 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
857 Py_DECREF(emptyTup);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
858 return ret;
24975
89c2bf63a83b lazymanifest: drop SP before some labels
Martin von Zweigbergk <martinvonz@google.com>
parents: 24974
diff changeset
859 nomem:
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
860 PyErr_NoMemory();
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
861 Py_XDECREF(ret);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
862 Py_XDECREF(emptyTup);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
863 return NULL;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
864 }
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
865
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
866 static PyMethodDef lazymanifest_methods[] = {
24295
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
867 {"iterkeys", (PyCFunction)lazymanifest_getkeysiter, METH_NOARGS,
2b7ab29627fd lazymanifest: add iterkeys() method
Martin von Zweigbergk <martinvonz@google.com>
parents: 24294
diff changeset
868 "Iterate over file names in this lazymanifest."},
24298
49cd847fd69a lazymanifest: make __iter__ generate filenames, not 3-tuples
Martin von Zweigbergk <martinvonz@google.com>
parents: 24295
diff changeset
869 {"iterentries", (PyCFunction)lazymanifest_getentriesiter, METH_NOARGS,
29254
c5912a0b156c lazymanifest: fix typo s/typles/tuples/
Javi Merino <merino.jav@gmail.com>
parents: 27661
diff changeset
870 "Iterate over (path, nodeid, flags) tuples in this lazymanifest."},
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
871 {"copy", (PyCFunction)lazymanifest_copy, METH_NOARGS,
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
872 "Make a copy of this lazymanifest."},
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
873 {"filtercopy", (PyCFunction)lazymanifest_filtercopy, METH_O,
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
874 "Make a copy of this manifest filtered by matchfn."},
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
875 {"diff", (PyCFunction)lazymanifest_diff, METH_VARARGS,
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
876 "Compare this lazymanifest to another one."},
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
877 {"text", (PyCFunction)lazymanifest_text, METH_NOARGS,
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
878 "Encode this manifest to text."},
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
879 {NULL},
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
880 };
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
881
30079
84debea79903 manifest: drop Py_TPFLAGS_HAVE_SEQUENCE_IN from tp_flags in Python 3
Gregory Szorc <gregory.szorc@gmail.com>
parents: 29254
diff changeset
882 #ifdef IS_PY3K
84debea79903 manifest: drop Py_TPFLAGS_HAVE_SEQUENCE_IN from tp_flags in Python 3
Gregory Szorc <gregory.szorc@gmail.com>
parents: 29254
diff changeset
883 #define LAZYMANIFEST_TPFLAGS Py_TPFLAGS_DEFAULT
84debea79903 manifest: drop Py_TPFLAGS_HAVE_SEQUENCE_IN from tp_flags in Python 3
Gregory Szorc <gregory.szorc@gmail.com>
parents: 29254
diff changeset
884 #else
84debea79903 manifest: drop Py_TPFLAGS_HAVE_SEQUENCE_IN from tp_flags in Python 3
Gregory Szorc <gregory.szorc@gmail.com>
parents: 29254
diff changeset
885 #define LAZYMANIFEST_TPFLAGS Py_TPFLAGS_DEFAULT | Py_TPFLAGS_HAVE_SEQUENCE_IN
84debea79903 manifest: drop Py_TPFLAGS_HAVE_SEQUENCE_IN from tp_flags in Python 3
Gregory Szorc <gregory.szorc@gmail.com>
parents: 29254
diff changeset
886 #endif
84debea79903 manifest: drop Py_TPFLAGS_HAVE_SEQUENCE_IN from tp_flags in Python 3
Gregory Szorc <gregory.szorc@gmail.com>
parents: 29254
diff changeset
887
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
888 static PyTypeObject lazymanifestType = {
30168
1a327889c13c manifest: use PyVarObject_HEAD_INIT
Gregory Szorc <gregory.szorc@gmail.com>
parents: 30097
diff changeset
889 PyVarObject_HEAD_INIT(NULL, 0)
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
890 "parsers.lazymanifest", /* tp_name */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
891 sizeof(lazymanifest), /* tp_basicsize */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
892 0, /* tp_itemsize */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
893 (destructor)lazymanifest_dealloc, /* tp_dealloc */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
894 0, /* tp_print */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
895 0, /* tp_getattr */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
896 0, /* tp_setattr */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
897 0, /* tp_compare */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
898 0, /* tp_repr */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
899 0, /* tp_as_number */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
900 &lazymanifest_seq_meths, /* tp_as_sequence */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
901 &lazymanifest_mapping_methods, /* tp_as_mapping */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
902 0, /* tp_hash */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
903 0, /* tp_call */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
904 0, /* tp_str */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
905 0, /* tp_getattro */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
906 0, /* tp_setattro */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
907 0, /* tp_as_buffer */
30079
84debea79903 manifest: drop Py_TPFLAGS_HAVE_SEQUENCE_IN from tp_flags in Python 3
Gregory Szorc <gregory.szorc@gmail.com>
parents: 29254
diff changeset
908 LAZYMANIFEST_TPFLAGS, /* tp_flags */
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
909 "TODO(augie)", /* tp_doc */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
910 0, /* tp_traverse */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
911 0, /* tp_clear */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
912 0, /* tp_richcompare */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
913 0, /* tp_weaklistoffset */
24298
49cd847fd69a lazymanifest: make __iter__ generate filenames, not 3-tuples
Martin von Zweigbergk <martinvonz@google.com>
parents: 24295
diff changeset
914 (getiterfunc)lazymanifest_getkeysiter, /* tp_iter */
24214
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
915 0, /* tp_iternext */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
916 lazymanifest_methods, /* tp_methods */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
917 0, /* tp_members */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
918 0, /* tp_getset */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
919 0, /* tp_base */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
920 0, /* tp_dict */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
921 0, /* tp_descr_get */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
922 0, /* tp_descr_set */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
923 0, /* tp_dictoffset */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
924 (initproc)lazymanifest_init, /* tp_init */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
925 0, /* tp_alloc */
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
926 };
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
927
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
928 void manifest_module_init(PyObject * mod)
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
929 {
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
930 lazymanifestType.tp_new = PyType_GenericNew;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
931 if (PyType_Ready(&lazymanifestType) < 0)
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
932 return;
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
933 Py_INCREF(&lazymanifestType);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
934
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
935 PyModule_AddObject(mod, "lazymanifest",
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
936 (PyObject *)&lazymanifestType);
a5f1bccd2996 manifest.c: new extension code to lazily parse manifests
Augie Fackler <augie@google.com>
parents:
diff changeset
937 }