saveload.c
changeset 2958 3f8946daf55f
parent 2952 6a26eeda9679
child 3043 cb8509834e42
equal deleted inserted replaced
2957:2bbb4add3410 2958:3f8946daf55f
   443  * sizes are guaranteed by assert_compiles in stdafx.h */
   443  * sizes are guaranteed by assert_compiles in stdafx.h */
   444 static const byte _conv_lengths[] = {1, 1, 2, 2, 4, 4, 8, 8, 2};
   444 static const byte _conv_lengths[] = {1, 1, 2, 2, 4, 4, 8, 8, 2};
   445 
   445 
   446 /**
   446 /**
   447  * Return the size in bytes of a certain type of normal/atomic variable
   447  * Return the size in bytes of a certain type of normal/atomic variable
   448  * @param var The variable the size is being asked of (NOTICE: unused)
       
   449  * @param conv @VarType type of variable that is used for calculating the size
   448  * @param conv @VarType type of variable that is used for calculating the size
   450  * @return Return the size of this type in byes
   449  * @return Return the size of this type in byes
   451  */
   450  */
   452 static inline size_t SlCalcConvLen(const void *var, VarType conv) {return _conv_lengths[conv & 0xF];}
   451 static inline size_t SlCalcConvLen(VarType conv)
       
   452 {
       
   453 	return _conv_lengths[conv & 0xF];
       
   454 }
   453 
   455 
   454 /**
   456 /**
   455  * Return the size in bytes of a reference (pointer)
   457  * Return the size in bytes of a reference (pointer)
   456  */
   458  */
   457 static inline size_t SlCalcRefLen(void) {return 2;}
   459 static inline size_t SlCalcRefLen(void) {return 2;}
   458 
   460 
   459 /**
   461 /**
   460  * Return the size in bytes of a certain type of atomic array
   462  * Return the size in bytes of a certain type of atomic array
   461  * @param array The variable the size is being asked of (NOTICE: unused)
       
   462  * @param length The length of the array counted in elements
   463  * @param length The length of the array counted in elements
   463  * @param conv @VarType type of the variable that is used in calculating the size
   464  * @param conv @VarType type of the variable that is used in calculating the size
   464  */
   465  */
   465 static inline size_t SlCalcArrayLen(const void *array, uint length, VarType conv) {return _conv_lengths[conv & 0xF] * length;}
   466 static inline size_t SlCalcArrayLen(uint length, VarType conv)
       
   467 {
       
   468 	return _conv_lengths[conv & 0xF] * length;
       
   469 }
   466 
   470 
   467 /**
   471 /**
   468  * Save/Load an array.
   472  * Save/Load an array.
   469  * @param array The array being manipulated
   473  * @param array The array being manipulated
   470  * @param length The length of the array in elements
   474  * @param length The length of the array in elements
   474 {
   478 {
   475 	static const byte conv_mem_size[] = {1, 1, 2, 2, 4, 4, 8, 8, 0};
   479 	static const byte conv_mem_size[] = {1, 1, 2, 2, 4, 4, 8, 8, 0};
   476 
   480 
   477 	// Automatically calculate the length?
   481 	// Automatically calculate the length?
   478 	if (_sl.need_length != NL_NONE) {
   482 	if (_sl.need_length != NL_NONE) {
   479 		SlSetLength(SlCalcArrayLen(array, length, conv));
   483 		SlSetLength(SlCalcArrayLen(length, conv));
   480 		// Determine length only?
   484 		// Determine length only?
   481 		if (_sl.need_length == NL_CALCLENGTH)
   485 		if (_sl.need_length == NL_CALCLENGTH)
   482 			return;
   486 			return;
   483 	}
   487 	}
   484 
   488 
   507 	}
   511 	}
   508 }
   512 }
   509 
   513 
   510 /**
   514 /**
   511  * Calculate the size of an object.
   515  * Calculate the size of an object.
   512  * @param object Object that needs its length calculated
       
   513  * @param sld The @SaveLoad description of the object so we know how to manipulate it
   516  * @param sld The @SaveLoad description of the object so we know how to manipulate it
   514  */
   517  */
   515 static size_t SlCalcObjLength(void *object, const SaveLoad *sld)
   518 static size_t SlCalcObjLength(const SaveLoad *sld)
   516 {
   519 {
   517 	size_t length = 0;
   520 	size_t length = 0;
   518 
   521 
   519 	// Need to determine the length and write a length tag.
   522 	// Need to determine the length and write a length tag.
   520 	for (; sld->cmd != SL_END; sld++) {
   523 	for (; sld->cmd != SL_END; sld++) {
   525 					continue;
   528 					continue;
   526 			}
   529 			}
   527 
   530 
   528 			switch (sld->cmd) {
   531 			switch (sld->cmd) {
   529 			case SL_VAR: case SL_CONDVAR: /* Normal Variable */
   532 			case SL_VAR: case SL_CONDVAR: /* Normal Variable */
   530 				length += SlCalcConvLen(NULL, sld->type); break;
   533 				length += SlCalcConvLen(sld->type); break;
   531 			case SL_REF: case SL_CONDREF:  /* Reference variable */
   534 			case SL_REF: case SL_CONDREF:  /* Reference variable */
   532 				length += SlCalcRefLen(); break;
   535 				length += SlCalcRefLen(); break;
   533 			case SL_ARR: case SL_CONDARR: /* Array */
   536 			case SL_ARR: case SL_CONDARR: /* Array */
   534 				length += SlCalcArrayLen(NULL, sld->length, sld->type); break;
   537 				length += SlCalcArrayLen(sld->length, sld->type); break;
   535 			default: NOT_REACHED();
   538 			default: NOT_REACHED();
   536 			}
   539 			}
   537 		} else if (sld->cmd == SL_WRITEBYTE) {
   540 		} else if (sld->cmd == SL_WRITEBYTE) {
   538 			length++; // a byte is logically of size 1
   541 			length++; // a byte is logically of size 1
   539 		} else if (sld->cmd == SL_INCLUDE) {
   542 		} else if (sld->cmd == SL_INCLUDE) {
   540 			length += SlCalcObjLength(NULL, _sl.includes[sld->version_from]);
   543 			length += SlCalcObjLength(_sl.includes[sld->version_from]);
   541 		} else
   544 		} else
   542 			assert(sld->cmd == SL_END);
   545 			assert(sld->cmd == SL_END);
   543 	}
   546 	}
   544 	return length;
   547 	return length;
   545 }
   548 }
   551  */
   554  */
   552 void SlObject(void *object, const SaveLoad *sld)
   555 void SlObject(void *object, const SaveLoad *sld)
   553 {
   556 {
   554 	// Automatically calculate the length?
   557 	// Automatically calculate the length?
   555 	if (_sl.need_length != NL_NONE) {
   558 	if (_sl.need_length != NL_NONE) {
   556 		SlSetLength(SlCalcObjLength(object, sld));
   559 		SlSetLength(SlCalcObjLength(sld));
   557 		if (_sl.need_length == NL_CALCLENGTH)
   560 		if (_sl.need_length == NL_CALCLENGTH)
   558 			return;
   561 			return;
   559 	}
   562 	}
   560 
   563 
   561 	for (; sld->cmd != SL_END; sld++) {
   564 	for (; sld->cmd != SL_END; sld++) {
   613 	size_t length = 0;
   616 	size_t length = 0;
   614 
   617 
   615 	for (; desc->address != NULL; desc++) {
   618 	for (; desc->address != NULL; desc++) {
   616 		// Of course the global variable must exist in the sought savegame version
   619 		// Of course the global variable must exist in the sought savegame version
   617 		if (_sl_version >= desc->from_version && _sl_version <= desc->to_version)
   620 		if (_sl_version >= desc->from_version && _sl_version <= desc->to_version)
   618 			length += SlCalcConvLen(NULL, desc->conv);
   621 			length += SlCalcConvLen(desc->conv);
   619 	}
   622 	}
   620 	return length;
   623 	return length;
   621 }
   624 }
   622 
   625 
   623 /**
   626 /**