Browse Source

[settings] Allow numeric_setting_value() to handle long setting values

Allow numeric_setting_value() to handle e.g. the byte sequence

  00:00:00:00:12:34:56:78

by returning -ERANGE only if the value actually overflows the return
type.

Signed-off-by: Michael Brown <mcb30@ipxe.org>
tags/v1.20.1
Michael Brown 11 years ago
parent
commit
55daa953fb
2 changed files with 10 additions and 4 deletions
  1. 4
    4
      src/core/settings.c
  2. 6
    0
      src/tests/settings_test.c

+ 4
- 4
src/core/settings.c View File

862
 	const int8_t *signed_bytes = raw;
862
 	const int8_t *signed_bytes = raw;
863
 	int is_negative;
863
 	int is_negative;
864
 	unsigned int i;
864
 	unsigned int i;
865
+	uint8_t pad;
865
 	uint8_t byte;
866
 	uint8_t byte;
866
 
867
 
867
-	/* Range check */
868
-	if ( len > sizeof ( long ) )
869
-		return -ERANGE;
870
-
871
 	/* Convert to host-ordered longs */
868
 	/* Convert to host-ordered longs */
872
 	is_negative = ( len && ( signed_bytes[0] < 0 ) );
869
 	is_negative = ( len && ( signed_bytes[0] < 0 ) );
873
 	*value = ( ( is_signed && is_negative ) ? -1L : 0 );
870
 	*value = ( ( is_signed && is_negative ) ? -1L : 0 );
871
+	pad = *value;
874
 	for ( i = 0 ; i < len ; i++ ) {
872
 	for ( i = 0 ; i < len ; i++ ) {
875
 		byte = unsigned_bytes[i];
873
 		byte = unsigned_bytes[i];
876
 		*value = ( ( *value << 8 ) | byte );
874
 		*value = ( ( *value << 8 ) | byte );
875
+		if ( ( ( i + sizeof ( *value ) ) < len ) && ( byte != pad ) )
876
+			return -ERANGE;
877
 	}
877
 	}
878
 
878
 
879
 	return len;
879
 	return len;

+ 6
- 0
src/tests/settings_test.c View File

342
 		    RAW ( 0x98, 0xab, 0x41, 0x81 ), 0x98ab4181 );
342
 		    RAW ( 0x98, 0xab, 0x41, 0x81 ), 0x98ab4181 );
343
 	fetchn_ok ( &test_settings, &test_uint32_setting,
343
 	fetchn_ok ( &test_settings, &test_uint32_setting,
344
 		    RAW ( 0xff, 0xff, 0xfe ), 0x00fffffe );
344
 		    RAW ( 0xff, 0xff, 0xfe ), 0x00fffffe );
345
+	fetchn_ok ( &test_settings, &test_uint32_setting,
346
+		    RAW ( 0, 0, 0, 0x12, 0x34, 0x56, 0x78 ), 0x12345678 );
347
+	fetchn_ok ( &test_settings, &test_int32_setting,
348
+		    RAW ( 0, 0, 0, 0x12, 0x34, 0x56, 0x78 ), 0x12345678 );
349
+	fetchn_ok ( &test_settings, &test_int32_setting,
350
+		    RAW ( 0xff, 0xff, 0x87, 0x65, 0x43, 0x21 ), -0x789abcdf );
345
 
351
 
346
 	/* "hex" setting type */
352
 	/* "hex" setting type */
347
 	storef_ok ( &test_settings, &test_hex_setting,
353
 	storef_ok ( &test_settings, &test_hex_setting,

Loading…
Cancel
Save