mercurial/cext/revlog.c
changeset 47256 2b69555e4875
parent 47251 6bfa6c2c5f15
child 47259 07641bafa646
equal deleted inserted replaced
47255:ff9fd7107d11 47256:2b69555e4875
   116 static Py_ssize_t inline_scan(indexObject *self, const char **offsets);
   116 static Py_ssize_t inline_scan(indexObject *self, const char **offsets);
   117 
   117 
   118 static int index_find_node(indexObject *self, const char *node);
   118 static int index_find_node(indexObject *self, const char *node);
   119 
   119 
   120 #if LONG_MAX == 0x7fffffffL
   120 #if LONG_MAX == 0x7fffffffL
   121 static const char *const tuple_format = PY23("Kiiiiiis#KiB", "Kiiiiiiy#KiB");
   121 static const char *const tuple_format = PY23("Kiiiiiis#KiBB", "Kiiiiiiy#KiBB");
   122 #else
   122 #else
   123 static const char *const tuple_format = PY23("kiiiiiis#kiB", "kiiiiiiy#kiB");
   123 static const char *const tuple_format = PY23("kiiiiiis#kiBB", "kiiiiiiy#kiBB");
   124 #endif
   124 #endif
   125 
   125 
   126 /* A RevlogNG v1 index entry is 64 bytes long. */
   126 /* A RevlogNG v1 index entry is 64 bytes long. */
   127 static const long v1_entry_size = 64;
   127 static const long v1_entry_size = 64;
   128 
   128 
   294 static PyObject *index_get(indexObject *self, Py_ssize_t pos)
   294 static PyObject *index_get(indexObject *self, Py_ssize_t pos)
   295 {
   295 {
   296 	uint64_t offset_flags, sidedata_offset;
   296 	uint64_t offset_flags, sidedata_offset;
   297 	int comp_len, uncomp_len, base_rev, link_rev, parent_1, parent_2,
   297 	int comp_len, uncomp_len, base_rev, link_rev, parent_1, parent_2,
   298 	    sidedata_comp_len;
   298 	    sidedata_comp_len;
   299 	char data_comp_mode;
   299 	char data_comp_mode, sidedata_comp_mode;
   300 	const char *c_node_id;
   300 	const char *c_node_id;
   301 	const char *data;
   301 	const char *data;
   302 	Py_ssize_t length = index_length(self);
   302 	Py_ssize_t length = index_length(self);
   303 
   303 
   304 	if (pos == nullrev) {
   304 	if (pos == nullrev) {
   337 
   337 
   338 	if (self->format_version == format_v1) {
   338 	if (self->format_version == format_v1) {
   339 		sidedata_offset = 0;
   339 		sidedata_offset = 0;
   340 		sidedata_comp_len = 0;
   340 		sidedata_comp_len = 0;
   341 		data_comp_mode = comp_mode_inline;
   341 		data_comp_mode = comp_mode_inline;
       
   342 		sidedata_comp_mode = comp_mode_inline;
   342 	} else {
   343 	} else {
   343 		sidedata_offset = getbe64(data + 64);
   344 		sidedata_offset = getbe64(data + 64);
   344 		sidedata_comp_len = getbe32(data + 72);
   345 		sidedata_comp_len = getbe32(data + 72);
   345 		data_comp_mode = data[76];
   346 		data_comp_mode = data[76] & 3;
       
   347 		sidedata_comp_mode = ((data[76] >> 2) & 3);
   346 	}
   348 	}
   347 
   349 
   348 	return Py_BuildValue(tuple_format, offset_flags, comp_len, uncomp_len,
   350 	return Py_BuildValue(tuple_format, offset_flags, comp_len, uncomp_len,
   349 	                     base_rev, link_rev, parent_1, parent_2, c_node_id,
   351 	                     base_rev, link_rev, parent_1, parent_2, c_node_id,
   350 	                     self->nodelen, sidedata_offset, sidedata_comp_len,
   352 	                     self->nodelen, sidedata_offset, sidedata_comp_len,
   351 	                     data_comp_mode);
   353 	                     data_comp_mode, sidedata_comp_mode);
   352 }
   354 }
   353 /*
   355 /*
   354  * Pack header information in binary
   356  * Pack header information in binary
   355  */
   357  */
   356 static PyObject *index_pack_header(indexObject *self, PyObject *args)
   358 static PyObject *index_pack_header(indexObject *self, PyObject *args)
   447 
   449 
   448 static PyObject *index_append(indexObject *self, PyObject *obj)
   450 static PyObject *index_append(indexObject *self, PyObject *obj)
   449 {
   451 {
   450 	uint64_t offset_flags, sidedata_offset;
   452 	uint64_t offset_flags, sidedata_offset;
   451 	int rev, comp_len, uncomp_len, base_rev, link_rev, parent_1, parent_2;
   453 	int rev, comp_len, uncomp_len, base_rev, link_rev, parent_1, parent_2;
   452 	char data_comp_mode;
   454 	char data_comp_mode, sidedata_comp_mode;
   453 	Py_ssize_t c_node_id_len, sidedata_comp_len;
   455 	Py_ssize_t c_node_id_len, sidedata_comp_len;
   454 	const char *c_node_id;
   456 	const char *c_node_id;
       
   457 	char comp_field;
   455 	char *data;
   458 	char *data;
   456 
   459 
   457 	if (!PyArg_ParseTuple(obj, tuple_format, &offset_flags, &comp_len,
   460 	if (!PyArg_ParseTuple(obj, tuple_format, &offset_flags, &comp_len,
   458 	                      &uncomp_len, &base_rev, &link_rev, &parent_1,
   461 	                      &uncomp_len, &base_rev, &link_rev, &parent_1,
   459 	                      &parent_2, &c_node_id, &c_node_id_len,
   462 	                      &parent_2, &c_node_id, &c_node_id_len,
   460 	                      &sidedata_offset, &sidedata_comp_len,
   463 	                      &sidedata_offset, &sidedata_comp_len,
   461 	                      &data_comp_mode)) {
   464 	                      &data_comp_mode, &sidedata_comp_mode)) {
   462 		PyErr_SetString(PyExc_TypeError, "11-tuple required");
   465 		PyErr_SetString(PyExc_TypeError, "11-tuple required");
   463 		return NULL;
   466 		return NULL;
   464 	}
   467 	}
   465 
   468 
   466 	if (c_node_id_len != self->nodelen) {
   469 	if (c_node_id_len != self->nodelen) {
   467 		PyErr_SetString(PyExc_TypeError, "invalid node");
   470 		PyErr_SetString(PyExc_TypeError, "invalid node");
   468 		return NULL;
   471 		return NULL;
   469 	}
   472 	}
   470 	if (self->format_version == format_v1 &&
   473 	if (self->format_version == format_v1) {
   471 	    data_comp_mode != comp_mode_inline) {
   474 
   472 		PyErr_Format(PyExc_ValueError,
   475 		if (data_comp_mode != comp_mode_inline) {
   473 		             "invalid data compression mode: %i",
   476 			PyErr_Format(PyExc_ValueError,
   474 		             data_comp_mode);
   477 			             "invalid data compression mode: %i",
   475 		return NULL;
   478 			             data_comp_mode);
       
   479 			return NULL;
       
   480 		}
       
   481 		if (sidedata_comp_mode != comp_mode_inline) {
       
   482 			PyErr_Format(PyExc_ValueError,
       
   483 			             "invalid sidedata compression mode: %i",
       
   484 			             sidedata_comp_mode);
       
   485 			return NULL;
       
   486 		}
   476 	}
   487 	}
   477 
   488 
   478 	if (self->new_length == self->added_length) {
   489 	if (self->new_length == self->added_length) {
   479 		size_t new_added_length =
   490 		size_t new_added_length =
   480 		    self->added_length ? self->added_length * 2 : 4096;
   491 		    self->added_length ? self->added_length * 2 : 4096;
   499 	/* Padding since SHA-1 is only 20 bytes for now */
   510 	/* Padding since SHA-1 is only 20 bytes for now */
   500 	memset(data + 32 + c_node_id_len, 0, 32 - c_node_id_len);
   511 	memset(data + 32 + c_node_id_len, 0, 32 - c_node_id_len);
   501 	if (self->format_version == format_v2) {
   512 	if (self->format_version == format_v2) {
   502 		putbe64(sidedata_offset, data + 64);
   513 		putbe64(sidedata_offset, data + 64);
   503 		putbe32(sidedata_comp_len, data + 72);
   514 		putbe32(sidedata_comp_len, data + 72);
   504 		data[76] = (char)data_comp_mode;
   515 		comp_field = data_comp_mode & 3;
       
   516 		comp_field = comp_field | (sidedata_comp_mode & 3) << 2;
       
   517 		data[76] = comp_field;
   505 		/* Padding for 96 bytes alignment */
   518 		/* Padding for 96 bytes alignment */
   506 		memset(data + 77, 0, self->entry_size - 77);
   519 		memset(data + 77, 0, self->entry_size - 77);
   507 	}
   520 	}
   508 
   521 
   509 	if (self->ntinitialized)
   522 	if (self->ntinitialized)
  2775 	} else {
  2788 	} else {
  2776 		self->format_version = format_v1;
  2789 		self->format_version = format_v1;
  2777 		self->entry_size = v1_entry_size;
  2790 		self->entry_size = v1_entry_size;
  2778 	}
  2791 	}
  2779 
  2792 
  2780 	self->nullentry = Py_BuildValue(PY23("iiiiiiis#iiB", "iiiiiiiy#iiB"), 0,
  2793 	self->nullentry = Py_BuildValue(
  2781 	                                0, 0, -1, -1, -1, -1, nullid,
  2794 	    PY23("iiiiiiis#iiBB", "iiiiiiiy#iiBB"), 0, 0, 0, -1, -1, -1, -1,
  2782 	                                self->nodelen, 0, 0, comp_mode_inline);
  2795 	    nullid, self->nodelen, 0, 0, comp_mode_inline, comp_mode_inline);
  2783 
  2796 
  2784 	if (!self->nullentry)
  2797 	if (!self->nullentry)
  2785 		return -1;
  2798 		return -1;
  2786 	PyObject_GC_UnTrack(self->nullentry);
  2799 	PyObject_GC_UnTrack(self->nullentry);
  2787 
  2800