mercurial/cext/revlog.c
changeset 48771 7dd5a2c0116a
parent 48770 654baf1faa52
child 48772 1bb62821f080
equal deleted inserted replaced
48770:654baf1faa52 48771:7dd5a2c0116a
   131 static const long v1_entry_size = 64;
   131 static const long v1_entry_size = 64;
   132 
   132 
   133 /* A Revlogv2 index entry is 96 bytes long. */
   133 /* A Revlogv2 index entry is 96 bytes long. */
   134 static const long v2_entry_size = 96;
   134 static const long v2_entry_size = 96;
   135 
   135 
   136 static const long format_v1 = 1; /* Internal only, could be any number */
   136 static const long format_v1 = 1;  /* Internal only, could be any number */
   137 static const long format_v2 = 2; /* Internal only, could be any number */
   137 static const long format_v2 = 2;  /* Internal only, could be any number */
       
   138 static const long format_cl2 = 3; /* Internal only, could be any number */
   138 
   139 
   139 static const long entry_v1_offset_high = 0;
   140 static const long entry_v1_offset_high = 0;
   140 static const long entry_v1_offset_offset_flags = 4;
   141 static const long entry_v1_offset_offset_flags = 4;
   141 static const long entry_v1_offset_comp_len = 8;
   142 static const long entry_v1_offset_comp_len = 8;
   142 static const long entry_v1_offset_uncomp_len = 12;
   143 static const long entry_v1_offset_uncomp_len = 12;
   158 static const long entry_v2_offset_sidedata_offset = 64;
   159 static const long entry_v2_offset_sidedata_offset = 64;
   159 static const long entry_v2_offset_sidedata_comp_len = 72;
   160 static const long entry_v2_offset_sidedata_comp_len = 72;
   160 static const long entry_v2_offset_all_comp_mode = 76;
   161 static const long entry_v2_offset_all_comp_mode = 76;
   161 /* next free offset: 77 */
   162 /* next free offset: 77 */
   162 
   163 
       
   164 static const long entry_cl2_offset_high = 0;
       
   165 static const long entry_cl2_offset_offset_flags = 4;
       
   166 static const long entry_cl2_offset_comp_len = 8;
       
   167 static const long entry_cl2_offset_uncomp_len = 12;
       
   168 static const long entry_cl2_offset_parent_1 = 16;
       
   169 static const long entry_cl2_offset_parent_2 = 20;
       
   170 static const long entry_cl2_offset_node_id = 24;
       
   171 static const long entry_cl2_offset_sidedata_offset = 56;
       
   172 static const long entry_cl2_offset_sidedata_comp_len = 64;
       
   173 static const long entry_cl2_offset_all_comp_mode = 68;
       
   174 static const long entry_cl2_offset_rank = 69;
       
   175 /* next free offset: 73 */
       
   176 
   163 static const char comp_mode_inline = 2;
   177 static const char comp_mode_inline = 2;
   164 static const char rank_unknown = -1;
   178 static const char rank_unknown = -1;
   165 
   179 
   166 static void raise_revlog_error(void)
   180 static void raise_revlog_error(void)
   167 {
   181 {
   234 		ps[0] = getbe32(data + entry_v1_offset_parent_1);
   248 		ps[0] = getbe32(data + entry_v1_offset_parent_1);
   235 		ps[1] = getbe32(data + entry_v1_offset_parent_2);
   249 		ps[1] = getbe32(data + entry_v1_offset_parent_2);
   236 	} else if (self->format_version == format_v2) {
   250 	} else if (self->format_version == format_v2) {
   237 		ps[0] = getbe32(data + entry_v2_offset_parent_1);
   251 		ps[0] = getbe32(data + entry_v2_offset_parent_1);
   238 		ps[1] = getbe32(data + entry_v2_offset_parent_2);
   252 		ps[1] = getbe32(data + entry_v2_offset_parent_2);
       
   253 	} else if (self->format_version == format_cl2) {
       
   254 		ps[0] = getbe32(data + entry_cl2_offset_parent_1);
       
   255 		ps[1] = getbe32(data + entry_cl2_offset_parent_2);
   239 	} else {
   256 	} else {
   240 		raise_revlog_error();
   257 		raise_revlog_error();
   241 		return -1;
   258 		return -1;
   242 	}
   259 	}
   243 
   260 
   305 		} else {
   322 		} else {
   306 			uint32_t offset_high =
   323 			uint32_t offset_high =
   307 			    getbe32(data + entry_v2_offset_high);
   324 			    getbe32(data + entry_v2_offset_high);
   308 			offset |= ((uint64_t)offset_high) << 32;
   325 			offset |= ((uint64_t)offset_high) << 32;
   309 		}
   326 		}
       
   327 	} else if (self->format_version == format_cl2) {
       
   328 		uint32_t offset_high = getbe32(data + entry_cl2_offset_high);
       
   329 		offset = getbe32(data + entry_cl2_offset_offset_flags);
       
   330 		offset |= ((uint64_t)offset_high) << 32;
   310 	} else {
   331 	} else {
   311 		raise_revlog_error();
   332 		raise_revlog_error();
   312 		return -1;
   333 		return -1;
   313 	}
   334 	}
   314 
   335 
   327 
   348 
   328 	if (self->format_version == format_v1) {
   349 	if (self->format_version == format_v1) {
   329 		tmp = (int)getbe32(data + entry_v1_offset_comp_len);
   350 		tmp = (int)getbe32(data + entry_v1_offset_comp_len);
   330 	} else if (self->format_version == format_v2) {
   351 	} else if (self->format_version == format_v2) {
   331 		tmp = (int)getbe32(data + entry_v2_offset_comp_len);
   352 		tmp = (int)getbe32(data + entry_v2_offset_comp_len);
       
   353 	} else if (self->format_version == format_cl2) {
       
   354 		tmp = (int)getbe32(data + entry_cl2_offset_comp_len);
   332 	} else {
   355 	} else {
   333 		raise_revlog_error();
   356 		raise_revlog_error();
   334 		return -1;
   357 		return -1;
   335 	}
   358 	}
   336 	if (tmp < 0) {
   359 	if (tmp < 0) {
   355  */
   378  */
   356 static PyObject *index_get(indexObject *self, Py_ssize_t pos)
   379 static PyObject *index_get(indexObject *self, Py_ssize_t pos)
   357 {
   380 {
   358 	uint64_t offset_flags, sidedata_offset;
   381 	uint64_t offset_flags, sidedata_offset;
   359 	int comp_len, uncomp_len, base_rev, link_rev, parent_1, parent_2,
   382 	int comp_len, uncomp_len, base_rev, link_rev, parent_1, parent_2,
   360 	    sidedata_comp_len;
   383 	    sidedata_comp_len, rank = rank_unknown;
   361 	char data_comp_mode, sidedata_comp_mode;
   384 	char data_comp_mode, sidedata_comp_mode;
   362 	const char *c_node_id;
   385 	const char *c_node_id;
   363 	const char *data;
   386 	const char *data;
   364 	Py_ssize_t length = index_length(self);
   387 	Py_ssize_t length = index_length(self);
   365 
   388 
   432 		sidedata_comp_len =
   455 		sidedata_comp_len =
   433 		    getbe32(data + entry_v2_offset_sidedata_comp_len);
   456 		    getbe32(data + entry_v2_offset_sidedata_comp_len);
   434 		data_comp_mode = data[entry_v2_offset_all_comp_mode] & 3;
   457 		data_comp_mode = data[entry_v2_offset_all_comp_mode] & 3;
   435 		sidedata_comp_mode =
   458 		sidedata_comp_mode =
   436 		    ((data[entry_v2_offset_all_comp_mode] >> 2) & 3);
   459 		    ((data[entry_v2_offset_all_comp_mode] >> 2) & 3);
       
   460 	} else if (self->format_version == format_cl2) {
       
   461 		uint32_t offset_high = getbe32(data + entry_cl2_offset_high);
       
   462 		offset_flags = getbe32(data + entry_cl2_offset_offset_flags);
       
   463 		offset_flags |= ((uint64_t)offset_high) << 32;
       
   464 		comp_len = getbe32(data + entry_cl2_offset_comp_len);
       
   465 		uncomp_len = getbe32(data + entry_cl2_offset_uncomp_len);
       
   466 		/* base_rev and link_rev are not stored in changelogv2, but are
       
   467 		 still used by some functions shared with the other revlogs.
       
   468 		 They are supposed to contain links to other revisions,
       
   469 		 but they always point to themselves in the case of a changelog.
       
   470 		*/
       
   471 		base_rev = pos;
       
   472 		link_rev = pos;
       
   473 		parent_1 = getbe32(data + entry_cl2_offset_parent_1);
       
   474 		parent_2 = getbe32(data + entry_cl2_offset_parent_2);
       
   475 		c_node_id = data + entry_cl2_offset_node_id;
       
   476 		sidedata_offset =
       
   477 		    getbe64(data + entry_cl2_offset_sidedata_offset);
       
   478 		sidedata_comp_len =
       
   479 		    getbe32(data + entry_cl2_offset_sidedata_comp_len);
       
   480 		data_comp_mode = data[entry_cl2_offset_all_comp_mode] & 3;
       
   481 		sidedata_comp_mode =
       
   482 		    ((data[entry_cl2_offset_all_comp_mode] >> 2) & 3);
       
   483 		rank = getbe32(data + entry_cl2_offset_rank);
   437 	} else {
   484 	} else {
   438 		raise_revlog_error();
   485 		raise_revlog_error();
   439 		return NULL;
   486 		return NULL;
   440 	}
   487 	}
   441 
   488 
   442 	return Py_BuildValue(tuple_format, offset_flags, comp_len, uncomp_len,
   489 	return Py_BuildValue(tuple_format, offset_flags, comp_len, uncomp_len,
   443 	                     base_rev, link_rev, parent_1, parent_2, c_node_id,
   490 	                     base_rev, link_rev, parent_1, parent_2, c_node_id,
   444 	                     self->nodelen, sidedata_offset, sidedata_comp_len,
   491 	                     self->nodelen, sidedata_offset, sidedata_comp_len,
   445 	                     data_comp_mode, sidedata_comp_mode, rank_unknown);
   492 	                     data_comp_mode, sidedata_comp_mode, rank);
   446 }
   493 }
   447 /*
   494 /*
   448  * Pack header information in binary
   495  * Pack header information in binary
   449  */
   496  */
   450 static PyObject *index_pack_header(indexObject *self, PyObject *args)
   497 static PyObject *index_pack_header(indexObject *self, PyObject *args)
   512 
   559 
   513 	if (self->format_version == format_v1) {
   560 	if (self->format_version == format_v1) {
   514 		node_id = data + entry_v1_offset_node_id;
   561 		node_id = data + entry_v1_offset_node_id;
   515 	} else if (self->format_version == format_v2) {
   562 	} else if (self->format_version == format_v2) {
   516 		node_id = data + entry_v2_offset_node_id;
   563 		node_id = data + entry_v2_offset_node_id;
       
   564 	} else if (self->format_version == format_cl2) {
       
   565 		node_id = data + entry_cl2_offset_node_id;
   517 	} else {
   566 	} else {
   518 		raise_revlog_error();
   567 		raise_revlog_error();
   519 		return NULL;
   568 		return NULL;
   520 	}
   569 	}
   521 
   570 
   634 		putbe32(sidedata_comp_len,
   683 		putbe32(sidedata_comp_len,
   635 		        data + entry_v2_offset_sidedata_comp_len);
   684 		        data + entry_v2_offset_sidedata_comp_len);
   636 		comp_field = data_comp_mode & 3;
   685 		comp_field = data_comp_mode & 3;
   637 		comp_field = comp_field | (sidedata_comp_mode & 3) << 2;
   686 		comp_field = comp_field | (sidedata_comp_mode & 3) << 2;
   638 		data[entry_v2_offset_all_comp_mode] = comp_field;
   687 		data[entry_v2_offset_all_comp_mode] = comp_field;
       
   688 	} else if (self->format_version == format_cl2) {
       
   689 		putbe32(offset_flags >> 32, data + entry_cl2_offset_high);
       
   690 		putbe32(offset_flags & 0xffffffffU,
       
   691 		        data + entry_cl2_offset_offset_flags);
       
   692 		putbe32(comp_len, data + entry_cl2_offset_comp_len);
       
   693 		putbe32(uncomp_len, data + entry_cl2_offset_uncomp_len);
       
   694 		putbe32(parent_1, data + entry_cl2_offset_parent_1);
       
   695 		putbe32(parent_2, data + entry_cl2_offset_parent_2);
       
   696 		memcpy(data + entry_cl2_offset_node_id, c_node_id,
       
   697 		       c_node_id_len);
       
   698 		putbe64(sidedata_offset,
       
   699 		        data + entry_cl2_offset_sidedata_offset);
       
   700 		putbe32(sidedata_comp_len,
       
   701 		        data + entry_cl2_offset_sidedata_comp_len);
       
   702 		comp_field = data_comp_mode & 3;
       
   703 		comp_field = comp_field | (sidedata_comp_mode & 3) << 2;
       
   704 		data[entry_cl2_offset_all_comp_mode] = comp_field;
       
   705 		putbe32(rank, data + entry_cl2_offset_rank);
   639 	} else {
   706 	} else {
   640 		raise_revlog_error();
   707 		raise_revlog_error();
   641 		return NULL;
   708 		return NULL;
   642 	}
   709 	}
   643 
   710 
   691 	}
   758 	}
   692 
   759 
   693 	/* Find the newly added node, offset from the "already on-disk" length
   760 	/* Find the newly added node, offset from the "already on-disk" length
   694 	 */
   761 	 */
   695 	data = self->added + self->entry_size * (rev - self->length);
   762 	data = self->added + self->entry_size * (rev - self->length);
   696 	putbe64(offset_flags, data + entry_v2_offset_high);
   763 	if (self->format_version == format_v2) {
   697 	putbe64(sidedata_offset, data + entry_v2_offset_sidedata_offset);
   764 		putbe64(offset_flags, data + entry_v2_offset_high);
   698 	putbe32(sidedata_comp_len, data + entry_v2_offset_sidedata_comp_len);
   765 		putbe64(sidedata_offset,
   699 	data[entry_v2_offset_all_comp_mode] =
   766 		        data + entry_v2_offset_sidedata_offset);
   700 	    (data[entry_v2_offset_all_comp_mode] & ~(3 << 2)) |
   767 		putbe32(sidedata_comp_len,
   701 	    ((comp_mode & 3) << 2);
   768 		        data + entry_v2_offset_sidedata_comp_len);
       
   769 		data[entry_v2_offset_all_comp_mode] =
       
   770 		    (data[entry_v2_offset_all_comp_mode] & ~(3 << 2)) |
       
   771 		    ((comp_mode & 3) << 2);
       
   772 	} else if (self->format_version == format_cl2) {
       
   773 		putbe64(offset_flags, data + entry_cl2_offset_high);
       
   774 		putbe64(sidedata_offset,
       
   775 		        data + entry_cl2_offset_sidedata_offset);
       
   776 		putbe32(sidedata_comp_len,
       
   777 		        data + entry_cl2_offset_sidedata_comp_len);
       
   778 		data[entry_cl2_offset_all_comp_mode] =
       
   779 		    (data[entry_cl2_offset_all_comp_mode] & ~(3 << 2)) |
       
   780 		    ((comp_mode & 3) << 2);
       
   781 	} else {
       
   782 		raise_revlog_error();
       
   783 		return NULL;
       
   784 	}
   702 
   785 
   703 	Py_RETURN_NONE;
   786 	Py_RETURN_NONE;
   704 }
   787 }
   705 
   788 
   706 static PyObject *index_stats(indexObject *self)
   789 static PyObject *index_stats(indexObject *self)
  1244 
  1327 
  1245 	if (self->format_version == format_v1) {
  1328 	if (self->format_version == format_v1) {
  1246 		result = getbe32(data + entry_v1_offset_base_rev);
  1329 		result = getbe32(data + entry_v1_offset_base_rev);
  1247 	} else if (self->format_version == format_v2) {
  1330 	} else if (self->format_version == format_v2) {
  1248 		result = getbe32(data + entry_v2_offset_base_rev);
  1331 		result = getbe32(data + entry_v2_offset_base_rev);
       
  1332 	} else if (self->format_version == format_cl2) {
       
  1333 		return rev;
  1249 	} else {
  1334 	} else {
  1250 		raise_revlog_error();
  1335 		raise_revlog_error();
  1251 		return -1;
  1336 		return -1;
  1252 	}
  1337 	}
  1253 
  1338