- Notifications
You must be signed in to change notification settings - Fork68
Expand file tree
/
Copy path_fun.c
More file actions
107 lines (89 loc) · 2.63 KB
/
_fun.c
File metadata and controls
107 lines (89 loc) · 2.63 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
#include<Python.h>
#include"_delta_apply.h"
staticPyObject*PackIndexFile_sha_to_index(PyObject*self,PyObject*args)
{
constunsignedchar*sha;
constunsignedintsha_len;
// Note: self is only set if we are a c type. We emulate an instance method,
// hence we have to get the instance as 'first' argument
// get instance and sha
PyObject*inst=0;
if (!PyArg_ParseTuple(args,"Os#",&inst,&sha,&sha_len))
returnNULL;
if (sha_len!=20) {
PyErr_SetString(PyExc_ValueError,"Sha is not 20 bytes long");
returnNULL;
}
if( !inst){
PyErr_SetString(PyExc_ValueError,"Cannot be called without self");
returnNULL;
}
// read lo and hi bounds
PyObject*fanout_table=PyObject_GetAttrString(inst,"_fanout_table");
if (!fanout_table){
PyErr_SetString(PyExc_ValueError,"Couldn't obtain fanout table");
returnNULL;
}
unsignedintlo=0,hi=0;
if (sha[0]){
PyObject*item=PySequence_GetItem(fanout_table, (constPy_ssize_t)(sha[0]-1));
lo=PyInt_AS_LONG(item);
Py_DECREF(item);
}
PyObject*item=PySequence_GetItem(fanout_table, (constPy_ssize_t)sha[0]);
hi=PyInt_AS_LONG(item);
Py_DECREF(item);
item=0;
Py_DECREF(fanout_table);
// get sha query function
PyObject*get_sha=PyObject_GetAttrString(inst,"sha");
if (!get_sha){
PyErr_SetString(PyExc_ValueError,"Couldn't obtain sha method");
returnNULL;
}
PyObject*sha_str=0;
while (lo<hi) {
constintmid= (lo+hi)/2;
sha_str=PyObject_CallFunction(get_sha,"i",mid);
if (!sha_str) {
returnNULL;
}
// we really trust that string ... for speed
constintcmp=memcmp(PyString_AS_STRING(sha_str),sha,20);
Py_DECREF(sha_str);
sha_str=0;
if (cmp<0){
lo=mid+1;
}
elseif (cmp>0) {
hi=mid;
}
else {
Py_DECREF(get_sha);
returnPyInt_FromLong(mid);
}// END handle comparison
}// END while lo < hi
// nothing found, cleanup
Py_DECREF(get_sha);
Py_RETURN_NONE;
}
staticPyMethodDefpy_fun[]= {
{"PackIndexFile_sha_to_index", (PyCFunction)PackIndexFile_sha_to_index,METH_VARARGS,"TODO" },
{"connect_deltas", (PyCFunction)connect_deltas,METH_O,"See python implementation" },
{"apply_delta", (PyCFunction)apply_delta,METH_VARARGS,"See python implementation" },
{NULL,NULL,0,NULL }
};
#ifndefPyMODINIT_FUNC/* declarations for DLL import/export */
#definePyMODINIT_FUNC void
#endif
PyMODINIT_FUNCinit_perf(void)
{
PyObject*m;
if (PyType_Ready(&DeltaChunkListType)<0)
return;
m=Py_InitModule3("_perf",py_fun,NULL);
if (m==NULL)
return;
Py_INCREF(&DeltaChunkListType);
PyModule_AddObject(m,"DeltaChunkList", (PyObject*)&DeltaChunkListType);
}