From d49b3272e1e2f2713622445d05d4001afb50bb7a Mon Sep 17 00:00:00 2001 From: Benedict Cohen Date: Mon, 2 Mar 2015 10:14:46 +0000 Subject: [PATCH 01/14] - Ignore user and shared data --- .gitignore | 4 ++++ 1 file changed, 4 insertions(+) create mode 100644 .gitignore diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..e3eb9ee --- /dev/null +++ b/.gitignore @@ -0,0 +1,4 @@ +JREnumTest/JREnumTest.xcodeproj/project.xcworkspace/xcshareddata/*.xccheckout +JREnumTest/JREnumTest.xcodeproj/project.xcworkspace/xcuserdata +JREnumTest/JREnumTest.xcodeproj/xcuserdata + From 10abbdeaafe5b672ea5721b4e7bd67857927999b Mon Sep 17 00:00:00 2001 From: Benedict Cohen Date: Mon, 2 Mar 2015 10:20:20 +0000 Subject: [PATCH 02/14] Added a dummy class that imports SplitEnums thus allowing for duplicate symbol errors to become apparent --- .../JREnumTest.xcodeproj/project.pbxproj | 6 +++++ JREnumTest/JREnumTest/DummyClass.h | 22 +++++++++++++++++++ JREnumTest/JREnumTest/DummyClass.m | 15 +++++++++++++ 3 files changed, 43 insertions(+) create mode 100644 JREnumTest/JREnumTest/DummyClass.h create mode 100644 JREnumTest/JREnumTest/DummyClass.m diff --git a/JREnumTest/JREnumTest.xcodeproj/project.pbxproj b/JREnumTest/JREnumTest.xcodeproj/project.pbxproj index 0164db9..cad807f 100644 --- a/JREnumTest/JREnumTest.xcodeproj/project.pbxproj +++ b/JREnumTest/JREnumTest.xcodeproj/project.pbxproj @@ -10,6 +10,7 @@ 795439BE16756A7C00B88D38 /* Foundation.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 795439BD16756A7C00B88D38 /* Foundation.framework */; }; 795439C116756A7C00B88D38 /* main.m in Sources */ = {isa = PBXBuildFile; fileRef = 795439C016756A7C00B88D38 /* main.m */; }; 795439CE16756AE000B88D38 /* SplitEnums.m in Sources */ = {isa = PBXBuildFile; fileRef = 795439CD16756AE000B88D38 /* SplitEnums.m */; }; + 827D16A11AA4701800B6E02B /* DummyClass.m in Sources */ = {isa = PBXBuildFile; fileRef = 827D16A01AA4701800B6E02B /* DummyClass.m */; }; /* End PBXBuildFile section */ /* Begin PBXCopyFilesBuildPhase section */ @@ -32,6 +33,8 @@ 795439CB16756A9200B88D38 /* JREnum.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = JREnum.h; path = ../../JREnum.h; sourceTree = ""; }; 795439CC16756AE000B88D38 /* SplitEnums.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = SplitEnums.h; sourceTree = ""; }; 795439CD16756AE000B88D38 /* SplitEnums.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = SplitEnums.m; sourceTree = ""; }; + 827D169F1AA4701800B6E02B /* DummyClass.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = DummyClass.h; sourceTree = ""; }; + 827D16A01AA4701800B6E02B /* DummyClass.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = DummyClass.m; sourceTree = ""; }; /* End PBXFileReference section */ /* Begin PBXFrameworksBuildPhase section */ @@ -77,6 +80,8 @@ 795439C016756A7C00B88D38 /* main.m */, 795439CC16756AE000B88D38 /* SplitEnums.h */, 795439CD16756AE000B88D38 /* SplitEnums.m */, + 827D169F1AA4701800B6E02B /* DummyClass.h */, + 827D16A01AA4701800B6E02B /* DummyClass.m */, 795439CB16756A9200B88D38 /* JREnum.h */, 795439C216756A7C00B88D38 /* Supporting Files */, ); @@ -142,6 +147,7 @@ isa = PBXSourcesBuildPhase; buildActionMask = 2147483647; files = ( + 827D16A11AA4701800B6E02B /* DummyClass.m in Sources */, 795439C116756A7C00B88D38 /* main.m in Sources */, 795439CE16756AE000B88D38 /* SplitEnums.m in Sources */, ); diff --git a/JREnumTest/JREnumTest/DummyClass.h b/JREnumTest/JREnumTest/DummyClass.h new file mode 100644 index 0000000..b5f254b --- /dev/null +++ b/JREnumTest/JREnumTest/DummyClass.h @@ -0,0 +1,22 @@ +// +// DummyClass.h +// JREnumTest +// +// Created by Benedict Cohen on 02/03/2015. +// Copyright (c) 2015 Jonathan 'Wolf' Rentzsch. All rights reserved. +// + +#import + + +/* + This file exists so that SplitEnums.h is #import-ed into more than one file so that duplicate symbol problems can be found in JREnum implementation. + */ + +#import "SplitEnums.h" + + + +@interface DummyClass : NSObject + +@end diff --git a/JREnumTest/JREnumTest/DummyClass.m b/JREnumTest/JREnumTest/DummyClass.m new file mode 100644 index 0000000..e6805e1 --- /dev/null +++ b/JREnumTest/JREnumTest/DummyClass.m @@ -0,0 +1,15 @@ +// +// DummyClass.m +// JREnumTest +// +// Created by Benedict Cohen on 02/03/2015. +// Copyright (c) 2015 Jonathan 'Wolf' Rentzsch. All rights reserved. +// + +#import "DummyClass.h" + + + +@implementation DummyClass + +@end From 05fa7acd0400b68db044c1333191126c589748a7 Mon Sep 17 00:00:00 2001 From: Benedict Cohen Date: Mon, 2 Mar 2015 10:48:10 +0000 Subject: [PATCH 03/14] Marked all functions as static and thus deprecated JREnumDefine/Declare. --- JREnum.h | 26 +++++++++----------------- 1 file changed, 9 insertions(+), 17 deletions(-) diff --git a/JREnum.h b/JREnum.h index 64cf5f0..49c696f 100644 --- a/JREnum.h +++ b/JREnum.h @@ -14,27 +14,19 @@ //-- #define JREnumDeclare(ENUM_TYPENAME, ENUM_CONSTANTS...) \ - typedef enum { \ - ENUM_CONSTANTS \ - } ENUM_TYPENAME; \ - extern NSDictionary* ENUM_TYPENAME##ByValue(); \ - extern NSDictionary* ENUM_TYPENAME##ByLabel(); \ - extern NSString* ENUM_TYPENAME##ToString(int enumValue); \ - extern BOOL ENUM_TYPENAME##FromString(NSString *enumLabel, ENUM_TYPENAME *enumValue); \ - _Pragma("clang diagnostic push") \ - _Pragma("clang diagnostic ignored \"-Wunused-variable\"") \ - static NSString *_##ENUM_TYPENAME##_constants_string = @"" #ENUM_CONSTANTS; \ - _Pragma("clang diagnostic pop") + _Pragma("GCC warning \"JREnumDeclare is deprecated and should be replaced with JREnum.\"") \ + JREnum(ENUM_TYPENAME, ENUM_CONSTANTS) //-- + #define JREnumDefine(ENUM_TYPENAME) \ - _JREnum_GenerateImplementation(ENUM_TYPENAME) + _Pragma("GCC warning \"JREnumDefine is deprecated and should be removed.\"") \ //-- #define _JREnum_GenerateImplementation(ENUM_TYPENAME) \ - NSArray* _JREnumParse##ENUM_TYPENAME##ConstantsString() { \ + static NSArray* _JREnumParse##ENUM_TYPENAME##ConstantsString() { \ NSString *constantsString = _##ENUM_TYPENAME##_constants_string; \ constantsString = [[constantsString componentsSeparatedByCharactersInSet:[NSCharacterSet whitespaceAndNewlineCharacterSet]] componentsJoinedByString:@""]; \ if ([constantsString hasSuffix:@","]) { \ @@ -68,7 +60,7 @@ return labelsAndValues; \ } \ \ - NSDictionary* ENUM_TYPENAME##ByValue() { \ + static NSDictionary* ENUM_TYPENAME##ByValue() { \ NSArray *constants = _JREnumParse##ENUM_TYPENAME##ConstantsString(); \ NSMutableDictionary *result = [NSMutableDictionary dictionaryWithCapacity:[constants count] / 2]; \ for (NSUInteger i = 0; i < [constants count]; i += 2) { \ @@ -79,7 +71,7 @@ return result; \ } \ \ - NSDictionary* ENUM_TYPENAME##ByLabel() { \ + static NSDictionary* ENUM_TYPENAME##ByLabel() { \ NSArray *constants = _JREnumParse##ENUM_TYPENAME##ConstantsString(); \ NSMutableDictionary *result = [NSMutableDictionary dictionaryWithCapacity:[constants count] / 2]; \ for (NSUInteger i = 0; i < [constants count]; i += 2) { \ @@ -90,7 +82,7 @@ return result; \ } \ \ - NSString* ENUM_TYPENAME##ToString(int enumValue) { \ + static NSString* ENUM_TYPENAME##ToString(int enumValue) { \ NSString *result = [ENUM_TYPENAME##ByValue() objectForKey:[NSNumber numberWithInt:enumValue]]; \ if (!result) { \ result = [NSString stringWithFormat:@"", enumValue]; \ @@ -98,7 +90,7 @@ return result; \ } \ \ - BOOL ENUM_TYPENAME##FromString(NSString *enumLabel, ENUM_TYPENAME *enumValue) { \ + static BOOL ENUM_TYPENAME##FromString(NSString *enumLabel, ENUM_TYPENAME *enumValue) { \ NSNumber *value = [ENUM_TYPENAME##ByLabel() objectForKey:enumLabel]; \ if (value) { \ *enumValue = (ENUM_TYPENAME)[value intValue]; \ From 2f2501802f6f2aa97b8e00b150271d3d3d25a99f Mon Sep 17 00:00:00 2001 From: Benedict Cohen Date: Mon, 2 Mar 2015 11:18:43 +0000 Subject: [PATCH 04/14] - Replaced enum with NS_ENUM --- JREnum.h | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/JREnum.h b/JREnum.h index 49c696f..4319b72 100644 --- a/JREnum.h +++ b/JREnum.h @@ -5,9 +5,9 @@ // https://github.com/rentzsch/JREnum #define JREnum(ENUM_TYPENAME, ENUM_CONSTANTS...) \ - typedef enum { \ + typedef NS_ENUM(NSInteger, ENUM_TYPENAME) { \ ENUM_CONSTANTS \ - } ENUM_TYPENAME; \ + }; \ static NSString *_##ENUM_TYPENAME##_constants_string = @"" #ENUM_CONSTANTS; \ _JREnum_GenerateImplementation(ENUM_TYPENAME) From 75219e10db4073de920c88a8e7588bbe80995a44 Mon Sep 17 00:00:00 2001 From: Benedict Cohen Date: Tue, 3 Mar 2015 09:56:43 +0000 Subject: [PATCH 05/14] Refactored To remove _JREnum_GenerateImplementation. It's no longer need due to now that JREnumDeclare is deprecated. --- JREnum.h | 158 +++++++++++++++++++++++++++---------------------------- 1 file changed, 78 insertions(+), 80 deletions(-) diff --git a/JREnum.h b/JREnum.h index 4319b72..0493821 100644 --- a/JREnum.h +++ b/JREnum.h @@ -5,11 +5,84 @@ // https://github.com/rentzsch/JREnum #define JREnum(ENUM_TYPENAME, ENUM_CONSTANTS...) \ - typedef NS_ENUM(NSInteger, ENUM_TYPENAME) { \ - ENUM_CONSTANTS \ - }; \ - static NSString *_##ENUM_TYPENAME##_constants_string = @"" #ENUM_CONSTANTS; \ - _JREnum_GenerateImplementation(ENUM_TYPENAME) +typedef NS_ENUM(NSInteger, ENUM_TYPENAME) { \ + ENUM_CONSTANTS \ +}; \ +\ +\ +static NSArray* _JREnumParse##ENUM_TYPENAME##ConstantsString() { \ + NSString *constantsString = @"" #ENUM_CONSTANTS; \ + constantsString = [[constantsString componentsSeparatedByCharactersInSet:[NSCharacterSet whitespaceAndNewlineCharacterSet]] componentsJoinedByString:@""]; \ + if ([constantsString hasSuffix:@","]) { \ + constantsString = [constantsString substringToIndex:[constantsString length]-1]; \ + } \ + NSArray *stringPairs = [constantsString componentsSeparatedByString:@","]; \ + NSMutableArray *labelsAndValues = [NSMutableArray arrayWithCapacity:[stringPairs count]]; \ + int nextDefaultValue = 0; \ + for (NSString *stringPair in stringPairs) { \ + NSArray *labelAndValueString = [stringPair componentsSeparatedByString:@"="]; \ + NSString *label = [labelAndValueString objectAtIndex:0]; \ + NSString *valueString = [labelAndValueString count] > 1 ? [labelAndValueString objectAtIndex:1] : nil; \ + int value; \ + if (valueString) { \ + NSRange shiftTokenRange = [valueString rangeOfString:@"<<"]; \ + if (shiftTokenRange.location != NSNotFound) { \ + valueString = [valueString substringFromIndex:shiftTokenRange.location + 2]; \ + value = 1 << [valueString intValue]; \ + } else if ([valueString hasPrefix:@"0x"]) { \ + [[NSScanner scannerWithString:valueString] scanHexInt:(unsigned int*)&value]; \ + } else { \ + value = [valueString intValue]; \ + } \ + } else { \ + value = nextDefaultValue; \ + } \ + nextDefaultValue = value + 1; \ + [labelsAndValues addObject:label]; \ + [labelsAndValues addObject:[NSNumber numberWithInt:value]]; \ + } \ + return labelsAndValues; \ +} \ +\ +static NSDictionary* ENUM_TYPENAME##ByValue() { \ + NSArray *constants = _JREnumParse##ENUM_TYPENAME##ConstantsString(); \ + NSMutableDictionary *result = [NSMutableDictionary dictionaryWithCapacity:[constants count] / 2]; \ + for (NSUInteger i = 0; i < [constants count]; i += 2) { \ + NSString *label = [constants objectAtIndex:i]; \ + NSNumber *value = [constants objectAtIndex:i+1]; \ + [result setObject:label forKey:value]; \ + } \ + return result; \ +} \ +\ +static NSDictionary* ENUM_TYPENAME##ByLabel() { \ + NSArray *constants = _JREnumParse##ENUM_TYPENAME##ConstantsString(); \ + NSMutableDictionary *result = [NSMutableDictionary dictionaryWithCapacity:[constants count] / 2]; \ + for (NSUInteger i = 0; i < [constants count]; i += 2) { \ + NSString *label = [constants objectAtIndex:i]; \ + NSNumber *value = [constants objectAtIndex:i+1]; \ + [result setObject:value forKey:label]; \ + } \ + return result; \ +} \ +\ +static NSString* ENUM_TYPENAME##ToString(int enumValue) { \ + NSString *result = [ENUM_TYPENAME##ByValue() objectForKey:[NSNumber numberWithInt:enumValue]]; \ + if (!result) { \ + result = [NSString stringWithFormat:@"", enumValue]; \ + } \ + return result; \ +} \ +\ +static BOOL ENUM_TYPENAME##FromString(NSString *enumLabel, ENUM_TYPENAME *enumValue) { \ + NSNumber *value = [ENUM_TYPENAME##ByLabel() objectForKey:enumLabel]; \ + if (value) { \ + *enumValue = (ENUM_TYPENAME)[value intValue]; \ + return YES; \ + } else { \ + return NO; \ + } \ +} //-- @@ -24,78 +97,3 @@ _Pragma("GCC warning \"JREnumDefine is deprecated and should be removed.\"") \ //-- - -#define _JREnum_GenerateImplementation(ENUM_TYPENAME) \ - static NSArray* _JREnumParse##ENUM_TYPENAME##ConstantsString() { \ - NSString *constantsString = _##ENUM_TYPENAME##_constants_string; \ - constantsString = [[constantsString componentsSeparatedByCharactersInSet:[NSCharacterSet whitespaceAndNewlineCharacterSet]] componentsJoinedByString:@""]; \ - if ([constantsString hasSuffix:@","]) { \ - constantsString = [constantsString substringToIndex:[constantsString length]-1]; \ - } \ - NSArray *stringPairs = [constantsString componentsSeparatedByString:@","]; \ - NSMutableArray *labelsAndValues = [NSMutableArray arrayWithCapacity:[stringPairs count]]; \ - int nextDefaultValue = 0; \ - for (NSString *stringPair in stringPairs) { \ - NSArray *labelAndValueString = [stringPair componentsSeparatedByString:@"="]; \ - NSString *label = [labelAndValueString objectAtIndex:0]; \ - NSString *valueString = [labelAndValueString count] > 1 ? [labelAndValueString objectAtIndex:1] : nil; \ - int value; \ - if (valueString) { \ - NSRange shiftTokenRange = [valueString rangeOfString:@"<<"]; \ - if (shiftTokenRange.location != NSNotFound) { \ - valueString = [valueString substringFromIndex:shiftTokenRange.location + 2]; \ - value = 1 << [valueString intValue]; \ - } else if ([valueString hasPrefix:@"0x"]) { \ - [[NSScanner scannerWithString:valueString] scanHexInt:(unsigned int*)&value]; \ - } else { \ - value = [valueString intValue]; \ - } \ - } else { \ - value = nextDefaultValue; \ - } \ - nextDefaultValue = value + 1; \ - [labelsAndValues addObject:label]; \ - [labelsAndValues addObject:[NSNumber numberWithInt:value]]; \ - } \ - return labelsAndValues; \ - } \ - \ - static NSDictionary* ENUM_TYPENAME##ByValue() { \ - NSArray *constants = _JREnumParse##ENUM_TYPENAME##ConstantsString(); \ - NSMutableDictionary *result = [NSMutableDictionary dictionaryWithCapacity:[constants count] / 2]; \ - for (NSUInteger i = 0; i < [constants count]; i += 2) { \ - NSString *label = [constants objectAtIndex:i]; \ - NSNumber *value = [constants objectAtIndex:i+1]; \ - [result setObject:label forKey:value]; \ - } \ - return result; \ - } \ - \ - static NSDictionary* ENUM_TYPENAME##ByLabel() { \ - NSArray *constants = _JREnumParse##ENUM_TYPENAME##ConstantsString(); \ - NSMutableDictionary *result = [NSMutableDictionary dictionaryWithCapacity:[constants count] / 2]; \ - for (NSUInteger i = 0; i < [constants count]; i += 2) { \ - NSString *label = [constants objectAtIndex:i]; \ - NSNumber *value = [constants objectAtIndex:i+1]; \ - [result setObject:value forKey:label]; \ - } \ - return result; \ - } \ - \ - static NSString* ENUM_TYPENAME##ToString(int enumValue) { \ - NSString *result = [ENUM_TYPENAME##ByValue() objectForKey:[NSNumber numberWithInt:enumValue]]; \ - if (!result) { \ - result = [NSString stringWithFormat:@"", enumValue]; \ - } \ - return result; \ - } \ - \ - static BOOL ENUM_TYPENAME##FromString(NSString *enumLabel, ENUM_TYPENAME *enumValue) { \ - NSNumber *value = [ENUM_TYPENAME##ByLabel() objectForKey:enumLabel]; \ - if (value) { \ - *enumValue = (ENUM_TYPENAME)[value intValue]; \ - return YES; \ - } else { \ - return NO; \ - } \ - } \ No newline at end of file From 3edba070b3413daee4d2c304e0cbed9a6021cb68 Mon Sep 17 00:00:00 2001 From: Benedict Cohen Date: Tue, 3 Mar 2015 10:39:55 +0000 Subject: [PATCH 06/14] Refactored guts of macro into functions (thus making them a lot easier to edit) --- JREnum.h | 145 ++++++++++++++++++++++++++++++++----------------------- 1 file changed, 85 insertions(+), 60 deletions(-) diff --git a/JREnum.h b/JREnum.h index 0493821..e02400d 100644 --- a/JREnum.h +++ b/JREnum.h @@ -4,84 +4,109 @@ // Some rights reserved: http://opensource.org/licenses/mit // https://github.com/rentzsch/JREnum +static NSArray* _JRPrivate_ParseEnumFromString(NSString *rawString) { + NSString *enumString = [[rawString componentsSeparatedByCharactersInSet:[NSCharacterSet whitespaceAndNewlineCharacterSet]] componentsJoinedByString:@""]; + if ([enumString hasSuffix:@","]) { + enumString = [enumString substringToIndex:[enumString length]-1]; + } + NSArray *stringPairs = [enumString componentsSeparatedByString:@","]; + NSMutableArray *labelsAndValues = [NSMutableArray arrayWithCapacity:[stringPairs count]]; + int nextDefaultValue = 0; + for (NSString *stringPair in stringPairs) { + NSArray *labelAndValueString = [stringPair componentsSeparatedByString:@"="]; + NSString *label = [labelAndValueString objectAtIndex:0]; + NSString *valueString = [labelAndValueString count] > 1 ? [labelAndValueString objectAtIndex:1] : nil; + int value; + if (valueString) { + NSRange shiftTokenRange = [valueString rangeOfString:@"<<"]; + if (shiftTokenRange.location != NSNotFound) { + valueString = [valueString substringFromIndex:shiftTokenRange.location + 2]; + value = 1 << [valueString intValue]; + } else if ([valueString hasPrefix:@"0x"]) { + [[NSScanner scannerWithString:valueString] scanHexInt:(unsigned int*)&value]; + } else { + value = [valueString intValue]; + } + } else { + value = nextDefaultValue; + } + nextDefaultValue = value + 1; + [labelsAndValues addObject:label]; + [labelsAndValues addObject:[NSNumber numberWithInt:value]]; + } + return labelsAndValues; +} + +static NSDictionary* _JRPrivate_EnumByValue(NSArray *constants) { + NSMutableDictionary *result = [NSMutableDictionary dictionaryWithCapacity:[constants count] / 2]; + for (NSUInteger i = 0; i < [constants count]; i += 2) { + NSString *label = [constants objectAtIndex:i]; + NSNumber *value = [constants objectAtIndex:i+1]; + [result setObject:label forKey:value]; + } + return result; +} + +static NSDictionary* _JRPrivate_EnumByLabel(NSArray *constants) { + NSMutableDictionary *result = [NSMutableDictionary dictionaryWithCapacity:[constants count] / 2]; + for (NSUInteger i = 0; i < [constants count]; i += 2) { + NSString *label = [constants objectAtIndex:i]; + NSNumber *value = [constants objectAtIndex:i+1]; + [result setObject:value forKey:label]; + } + return result; +} + +static NSString* _JRPrivate_EnumToString(NSArray *constants, NSString *enumTypeName, int enumValue) { + NSString *result = [_JRPrivate_EnumByValue(constants) objectForKey:[NSNumber numberWithInt:enumValue]]; + if (!result) { + result = [NSString stringWithFormat:@"", enumTypeName, enumValue]; + } + return result; +} + +static BOOL _JRPrivate_EnumFromString(NSArray *constants, NSString *enumLabel, NSInteger *enumValue) { + NSNumber *value = [_JRPrivate_EnumByLabel(constants) objectForKey:enumLabel]; + if (value) { + *enumValue = [value integerValue]; + return YES; + } else { + return NO; + } +} + + + #define JREnum(ENUM_TYPENAME, ENUM_CONSTANTS...) \ typedef NS_ENUM(NSInteger, ENUM_TYPENAME) { \ ENUM_CONSTANTS \ }; \ \ \ -static NSArray* _JREnumParse##ENUM_TYPENAME##ConstantsString() { \ +static NSArray* _##ENUM_TYPENAME##KeysAndValues() { \ NSString *constantsString = @"" #ENUM_CONSTANTS; \ - constantsString = [[constantsString componentsSeparatedByCharactersInSet:[NSCharacterSet whitespaceAndNewlineCharacterSet]] componentsJoinedByString:@""]; \ - if ([constantsString hasSuffix:@","]) { \ - constantsString = [constantsString substringToIndex:[constantsString length]-1]; \ - } \ - NSArray *stringPairs = [constantsString componentsSeparatedByString:@","]; \ - NSMutableArray *labelsAndValues = [NSMutableArray arrayWithCapacity:[stringPairs count]]; \ - int nextDefaultValue = 0; \ - for (NSString *stringPair in stringPairs) { \ - NSArray *labelAndValueString = [stringPair componentsSeparatedByString:@"="]; \ - NSString *label = [labelAndValueString objectAtIndex:0]; \ - NSString *valueString = [labelAndValueString count] > 1 ? [labelAndValueString objectAtIndex:1] : nil; \ - int value; \ - if (valueString) { \ - NSRange shiftTokenRange = [valueString rangeOfString:@"<<"]; \ - if (shiftTokenRange.location != NSNotFound) { \ - valueString = [valueString substringFromIndex:shiftTokenRange.location + 2]; \ - value = 1 << [valueString intValue]; \ - } else if ([valueString hasPrefix:@"0x"]) { \ - [[NSScanner scannerWithString:valueString] scanHexInt:(unsigned int*)&value]; \ - } else { \ - value = [valueString intValue]; \ - } \ - } else { \ - value = nextDefaultValue; \ - } \ - nextDefaultValue = value + 1; \ - [labelsAndValues addObject:label]; \ - [labelsAndValues addObject:[NSNumber numberWithInt:value]]; \ - } \ - return labelsAndValues; \ -} \ + return _JRPrivate_ParseEnumFromString(constantsString); \ +} \ \ static NSDictionary* ENUM_TYPENAME##ByValue() { \ - NSArray *constants = _JREnumParse##ENUM_TYPENAME##ConstantsString(); \ - NSMutableDictionary *result = [NSMutableDictionary dictionaryWithCapacity:[constants count] / 2]; \ - for (NSUInteger i = 0; i < [constants count]; i += 2) { \ - NSString *label = [constants objectAtIndex:i]; \ - NSNumber *value = [constants objectAtIndex:i+1]; \ - [result setObject:label forKey:value]; \ - } \ - return result; \ + NSArray *constants = _##ENUM_TYPENAME##KeysAndValues(); \ + return _JRPrivate_EnumByValue(constants); \ } \ \ static NSDictionary* ENUM_TYPENAME##ByLabel() { \ - NSArray *constants = _JREnumParse##ENUM_TYPENAME##ConstantsString(); \ - NSMutableDictionary *result = [NSMutableDictionary dictionaryWithCapacity:[constants count] / 2]; \ - for (NSUInteger i = 0; i < [constants count]; i += 2) { \ - NSString *label = [constants objectAtIndex:i]; \ - NSNumber *value = [constants objectAtIndex:i+1]; \ - [result setObject:value forKey:label]; \ - } \ - return result; \ + NSArray *constants = _##ENUM_TYPENAME##KeysAndValues(); \ + return _JRPrivate_EnumByLabel(constants); \ } \ \ static NSString* ENUM_TYPENAME##ToString(int enumValue) { \ - NSString *result = [ENUM_TYPENAME##ByValue() objectForKey:[NSNumber numberWithInt:enumValue]]; \ - if (!result) { \ - result = [NSString stringWithFormat:@"", enumValue]; \ - } \ - return result; \ + NSArray *constants = _##ENUM_TYPENAME##KeysAndValues(); \ + NSString *enumTypeName = @"" #ENUM_TYPENAME; \ + return _JRPrivate_EnumToString(constants, enumTypeName, enumValue); \ } \ \ static BOOL ENUM_TYPENAME##FromString(NSString *enumLabel, ENUM_TYPENAME *enumValue) { \ - NSNumber *value = [ENUM_TYPENAME##ByLabel() objectForKey:enumLabel]; \ - if (value) { \ - *enumValue = (ENUM_TYPENAME)[value intValue]; \ - return YES; \ - } else { \ - return NO; \ - } \ + NSArray *constants = _##ENUM_TYPENAME##KeysAndValues(); \ + return _JRPrivate_EnumFromString(constants, enumLabel, enumValue); \ } //-- From 3489b8a2da07282898594f8697d02e3125c3dcf2 Mon Sep 17 00:00:00 2001 From: Benedict Cohen Date: Tue, 3 Mar 2015 10:46:21 +0000 Subject: [PATCH 07/14] Standardized naming (enums are referred to as 'labels' and 'keys') --- JREnum.h | 52 ++++++++++++++++++++++++++-------------------------- 1 file changed, 26 insertions(+), 26 deletions(-) diff --git a/JREnum.h b/JREnum.h index e02400d..a9aab6b 100644 --- a/JREnum.h +++ b/JREnum.h @@ -4,7 +4,7 @@ // Some rights reserved: http://opensource.org/licenses/mit // https://github.com/rentzsch/JREnum -static NSArray* _JRPrivate_ParseEnumFromString(NSString *rawString) { +static NSArray* _JRPrivate_ParseEnumLabelsAndValuesFromString(NSString *rawString) { NSString *enumString = [[rawString componentsSeparatedByCharactersInSet:[NSCharacterSet whitespaceAndNewlineCharacterSet]] componentsJoinedByString:@""]; if ([enumString hasSuffix:@","]) { enumString = [enumString substringToIndex:[enumString length]-1]; @@ -37,36 +37,36 @@ static NSArray* _JRPrivate_ParseEnumFromString(NSString *rawString) { return labelsAndValues; } -static NSDictionary* _JRPrivate_EnumByValue(NSArray *constants) { - NSMutableDictionary *result = [NSMutableDictionary dictionaryWithCapacity:[constants count] / 2]; - for (NSUInteger i = 0; i < [constants count]; i += 2) { - NSString *label = [constants objectAtIndex:i]; - NSNumber *value = [constants objectAtIndex:i+1]; +static NSDictionary* _JRPrivate_EnumByValue(NSArray *labelsAndValues) { + NSMutableDictionary *result = [NSMutableDictionary dictionaryWithCapacity:[labelsAndValues count] / 2]; + for (NSUInteger i = 0; i < [labelsAndValues count]; i += 2) { + NSString *label = [labelsAndValues objectAtIndex:i]; + NSNumber *value = [labelsAndValues objectAtIndex:i+1]; [result setObject:label forKey:value]; } return result; } -static NSDictionary* _JRPrivate_EnumByLabel(NSArray *constants) { - NSMutableDictionary *result = [NSMutableDictionary dictionaryWithCapacity:[constants count] / 2]; - for (NSUInteger i = 0; i < [constants count]; i += 2) { - NSString *label = [constants objectAtIndex:i]; - NSNumber *value = [constants objectAtIndex:i+1]; +static NSDictionary* _JRPrivate_EnumByLabel(NSArray *labelsAndValues) { + NSMutableDictionary *result = [NSMutableDictionary dictionaryWithCapacity:[labelsAndValues count] / 2]; + for (NSUInteger i = 0; i < [labelsAndValues count]; i += 2) { + NSString *label = [labelsAndValues objectAtIndex:i]; + NSNumber *value = [labelsAndValues objectAtIndex:i+1]; [result setObject:value forKey:label]; } return result; } -static NSString* _JRPrivate_EnumToString(NSArray *constants, NSString *enumTypeName, int enumValue) { - NSString *result = [_JRPrivate_EnumByValue(constants) objectForKey:[NSNumber numberWithInt:enumValue]]; +static NSString* _JRPrivate_EnumToString(NSArray *labelsAndValues, NSString *enumTypeName, int enumValue) { + NSString *result = [_JRPrivate_EnumByValue(labelsAndValues) objectForKey:[NSNumber numberWithInt:enumValue]]; if (!result) { result = [NSString stringWithFormat:@"", enumTypeName, enumValue]; } return result; } -static BOOL _JRPrivate_EnumFromString(NSArray *constants, NSString *enumLabel, NSInteger *enumValue) { - NSNumber *value = [_JRPrivate_EnumByLabel(constants) objectForKey:enumLabel]; +static BOOL _JRPrivate_EnumFromString(NSArray *labelsAndValues, NSString *enumLabel, NSInteger *enumValue) { + NSNumber *value = [_JRPrivate_EnumByLabel(labelsAndValues) objectForKey:enumLabel]; if (value) { *enumValue = [value integerValue]; return YES; @@ -83,30 +83,30 @@ typedef NS_ENUM(NSInteger, ENUM_TYPENAME) { \ }; \ \ \ -static NSArray* _##ENUM_TYPENAME##KeysAndValues() { \ - NSString *constantsString = @"" #ENUM_CONSTANTS; \ - return _JRPrivate_ParseEnumFromString(constantsString); \ +static NSArray* _##ENUM_TYPENAME##LabelsAndValues() { \ + NSString *enumString = @"" #ENUM_CONSTANTS; \ + return _JRPrivate_ParseEnumLabelsAndValuesFromString(enumString); \ } \ \ static NSDictionary* ENUM_TYPENAME##ByValue() { \ - NSArray *constants = _##ENUM_TYPENAME##KeysAndValues(); \ - return _JRPrivate_EnumByValue(constants); \ + NSArray *labelsAndValues = _##ENUM_TYPENAME##LabelsAndValues(); \ + return _JRPrivate_EnumByValue(labelsAndValues); \ } \ \ static NSDictionary* ENUM_TYPENAME##ByLabel() { \ - NSArray *constants = _##ENUM_TYPENAME##KeysAndValues(); \ - return _JRPrivate_EnumByLabel(constants); \ + NSArray *labelsAndValues = _##ENUM_TYPENAME##LabelsAndValues(); \ + return _JRPrivate_EnumByLabel(labelsAndValues); \ } \ \ static NSString* ENUM_TYPENAME##ToString(int enumValue) { \ - NSArray *constants = _##ENUM_TYPENAME##KeysAndValues(); \ + NSArray *labelsAndValues = _##ENUM_TYPENAME##LabelsAndValues(); \ NSString *enumTypeName = @"" #ENUM_TYPENAME; \ - return _JRPrivate_EnumToString(constants, enumTypeName, enumValue); \ + return _JRPrivate_EnumToString(labelsAndValues, enumTypeName, enumValue); \ } \ \ static BOOL ENUM_TYPENAME##FromString(NSString *enumLabel, ENUM_TYPENAME *enumValue) { \ - NSArray *constants = _##ENUM_TYPENAME##KeysAndValues(); \ - return _JRPrivate_EnumFromString(constants, enumLabel, enumValue); \ + NSArray *labelsAndValues = _##ENUM_TYPENAME##LabelsAndValues(); \ + return _JRPrivate_EnumFromString(labelsAndValues, enumLabel, enumValue); \ } //-- From f46b31d9816818675df65605b2915e61e8bd0247 Mon Sep 17 00:00:00 2001 From: Benedict Cohen Date: Tue, 3 Mar 2015 10:50:21 +0000 Subject: [PATCH 08/14] - Added `#pragma mark`s --- JREnum.h | 9 ++++++++- 1 file changed, 8 insertions(+), 1 deletion(-) diff --git a/JREnum.h b/JREnum.h index a9aab6b..98cd4e7 100644 --- a/JREnum.h +++ b/JREnum.h @@ -4,6 +4,8 @@ // Some rights reserved: http://opensource.org/licenses/mit // https://github.com/rentzsch/JREnum +#pragma mark - Private functions (called by functions defined in macros) + static NSArray* _JRPrivate_ParseEnumLabelsAndValuesFromString(NSString *rawString) { NSString *enumString = [[rawString componentsSeparatedByCharactersInSet:[NSCharacterSet whitespaceAndNewlineCharacterSet]] componentsJoinedByString:@""]; if ([enumString hasSuffix:@","]) { @@ -77,6 +79,9 @@ static BOOL _JRPrivate_EnumFromString(NSArray *labelsAndValues, NSString *enumLa +#pragma mark - JREnum macro +//-- + #define JREnum(ENUM_TYPENAME, ENUM_CONSTANTS...) \ typedef NS_ENUM(NSInteger, ENUM_TYPENAME) { \ ENUM_CONSTANTS \ @@ -109,6 +114,9 @@ static BOOL ENUM_TYPENAME##FromString(NSString *enumLabel, ENUM_TYPENAME *enumVa return _JRPrivate_EnumFromString(labelsAndValues, enumLabel, enumValue); \ } + + +#pragma mark - Deprecated macros //-- #define JREnumDeclare(ENUM_TYPENAME, ENUM_CONSTANTS...) \ @@ -117,7 +125,6 @@ static BOOL ENUM_TYPENAME##FromString(NSString *enumLabel, ENUM_TYPENAME *enumVa //-- - #define JREnumDefine(ENUM_TYPENAME) \ _Pragma("GCC warning \"JREnumDefine is deprecated and should be removed.\"") \ From 2d65c61d1ec2674da9e130813b9bf9527d801600 Mon Sep 17 00:00:00 2001 From: Benedict Cohen Date: Tue, 3 Mar 2015 11:21:14 +0000 Subject: [PATCH 09/14] Added documentation/comments --- JREnum.h | 56 ++++++++++++++++++++++++++++++++++++++++++++++++++------ 1 file changed, 50 insertions(+), 6 deletions(-) diff --git a/JREnum.h b/JREnum.h index 98cd4e7..8390bc6 100644 --- a/JREnum.h +++ b/JREnum.h @@ -5,13 +5,25 @@ // https://github.com/rentzsch/JREnum #pragma mark - Private functions (called by functions defined in macros) - -static NSArray* _JRPrivate_ParseEnumLabelsAndValuesFromString(NSString *rawString) { - NSString *enumString = [[rawString componentsSeparatedByCharactersInSet:[NSCharacterSet whitespaceAndNewlineCharacterSet]] componentsJoinedByString:@""]; - if ([enumString hasSuffix:@","]) { - enumString = [enumString substringToIndex:[enumString length]-1]; +/** + Parses enumString into an array of interleaved labels and keys. + + TODO: Document restrictions on key. The follow, for example, will have strange results: + 1. JREnumValue = NSNotFound + 2. JREnumNewValue = 0, JRValueOldEnum = JREnumNewValue, + 3. ArfVoid = 0, Arf1, Arf2 = (Arf1 * (2 + ArfVoid)), + It's possible to improve the function so that it can parse cases 2 and 3 but not case 1. + + @param enumString a string of comma delimitted labels and optional keys that form a valid C enum body. + + @return an array of interleaved labels and keys. + */ +static NSArray* _JRPrivate_ParseEnumLabelsAndValuesFromString(NSString *enumString) { + NSString *normalized = [[enumString componentsSeparatedByCharactersInSet:[NSCharacterSet whitespaceAndNewlineCharacterSet]] componentsJoinedByString:@""]; + if ([normalized hasSuffix:@","]) { + normalized = [normalized substringToIndex:[normalized length]-1]; } - NSArray *stringPairs = [enumString componentsSeparatedByString:@","]; + NSArray *stringPairs = [normalized componentsSeparatedByString:@","]; NSMutableArray *labelsAndValues = [NSMutableArray arrayWithCapacity:[stringPairs count]]; int nextDefaultValue = 0; for (NSString *stringPair in stringPairs) { @@ -39,6 +51,13 @@ static NSArray* _JRPrivate_ParseEnumLabelsAndValuesFromString(NSString *rawStrin return labelsAndValues; } +/** + Converts a labels & values array into a dictionary. If multiple labels have the same value then the dictionary will contain the last matching label. + + @param labelsAndValues An array of interleaved labels and values. + + @return a dictionary were the keys are the enum values and the values are the enum labels. + */ static NSDictionary* _JRPrivate_EnumByValue(NSArray *labelsAndValues) { NSMutableDictionary *result = [NSMutableDictionary dictionaryWithCapacity:[labelsAndValues count] / 2]; for (NSUInteger i = 0; i < [labelsAndValues count]; i += 2) { @@ -49,6 +68,13 @@ static NSDictionary* _JRPrivate_EnumByValue(NSArray *labelsAndValues) { return result; } +/** + Converts a labels & values array into a dictionary. + + @param labelsAndValues An array of interleaved labels and values. + + @return a dictionary were the keys are the enum labels and the values and the enum values. + */ static NSDictionary* _JRPrivate_EnumByLabel(NSArray *labelsAndValues) { NSMutableDictionary *result = [NSMutableDictionary dictionaryWithCapacity:[labelsAndValues count] / 2]; for (NSUInteger i = 0; i < [labelsAndValues count]; i += 2) { @@ -59,6 +85,15 @@ static NSDictionary* _JRPrivate_EnumByLabel(NSArray *labelsAndValues) { return result; } +/** + Returns an enum label as a string for the given enum value. If multiple labels have the same value then the result will be the label that was defined latest in the enum. + + @param labelsAndValues An array of interleaved labels and values. + @param enumTypeName The name of the enum. + @param enumValue The value to lookup. + + @return The label for enumValue. + */ static NSString* _JRPrivate_EnumToString(NSArray *labelsAndValues, NSString *enumTypeName, int enumValue) { NSString *result = [_JRPrivate_EnumByValue(labelsAndValues) objectForKey:[NSNumber numberWithInt:enumValue]]; if (!result) { @@ -67,6 +102,15 @@ static NSString* _JRPrivate_EnumToString(NSArray *labelsAndValues, NSString *enu return result; } +/** + Returns by reference the the value for the specified label. + + @param labelsAndValues An array of interleaved labels and values. + @param enumLabel The label to lookup. + @param enumValue On return contains the value for the specified label. + + @return YES on success otherwise NO. + */ static BOOL _JRPrivate_EnumFromString(NSArray *labelsAndValues, NSString *enumLabel, NSInteger *enumValue) { NSNumber *value = [_JRPrivate_EnumByLabel(labelsAndValues) objectForKey:enumLabel]; if (value) { From 97adf2895d142beda630f6ea6c6ad5a76ae6cf5f Mon Sep 17 00:00:00 2001 From: Benedict Cohen Date: Tue, 3 Mar 2015 11:21:43 +0000 Subject: [PATCH 10/14] Added none attribute annotations --- JREnum.h | 2 ++ 1 file changed, 2 insertions(+) diff --git a/JREnum.h b/JREnum.h index 8390bc6..447b8ae 100644 --- a/JREnum.h +++ b/JREnum.h @@ -111,6 +111,7 @@ static NSString* _JRPrivate_EnumToString(NSArray *labelsAndValues, NSString *enu @return YES on success otherwise NO. */ +static BOOL _JRPrivate_EnumFromString(NSArray *labelsAndValues, NSString *enumLabel, NSInteger *enumValue) __attribute__((nonnull(3))); static BOOL _JRPrivate_EnumFromString(NSArray *labelsAndValues, NSString *enumLabel, NSInteger *enumValue) { NSNumber *value = [_JRPrivate_EnumByLabel(labelsAndValues) objectForKey:enumLabel]; if (value) { @@ -153,6 +154,7 @@ static NSString* ENUM_TYPENAME##ToString(int enumValue) { \ return _JRPrivate_EnumToString(labelsAndValues, enumTypeName, enumValue); \ } \ \ +static BOOL ENUM_TYPENAME##FromString(NSString *enumLabel, ENUM_TYPENAME *enumValue) __attribute__((nonnull(2))); \ static BOOL ENUM_TYPENAME##FromString(NSString *enumLabel, ENUM_TYPENAME *enumValue) { \ NSArray *labelsAndValues = _##ENUM_TYPENAME##LabelsAndValues(); \ return _JRPrivate_EnumFromString(labelsAndValues, enumLabel, enumValue); \ From 1f1b01a33b0e1140750234701a5bc6c385d153bf Mon Sep 17 00:00:00 2001 From: Benedict Cohen Date: Tue, 3 Mar 2015 11:24:45 +0000 Subject: [PATCH 11/14] Changed int to NSInteger for values because we're using NS_ENUM with NSInteger --- JREnum.h | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/JREnum.h b/JREnum.h index 447b8ae..8402d37 100644 --- a/JREnum.h +++ b/JREnum.h @@ -25,12 +25,12 @@ static NSArray* _JRPrivate_ParseEnumLabelsAndValuesFromString(NSString *enumStri } NSArray *stringPairs = [normalized componentsSeparatedByString:@","]; NSMutableArray *labelsAndValues = [NSMutableArray arrayWithCapacity:[stringPairs count]]; - int nextDefaultValue = 0; + NSInteger nextDefaultValue = 0; for (NSString *stringPair in stringPairs) { NSArray *labelAndValueString = [stringPair componentsSeparatedByString:@"="]; NSString *label = [labelAndValueString objectAtIndex:0]; NSString *valueString = [labelAndValueString count] > 1 ? [labelAndValueString objectAtIndex:1] : nil; - int value; + NSInteger value; if (valueString) { NSRange shiftTokenRange = [valueString rangeOfString:@"<<"]; if (shiftTokenRange.location != NSNotFound) { @@ -94,7 +94,7 @@ static NSDictionary* _JRPrivate_EnumByLabel(NSArray *labelsAndValues) { @return The label for enumValue. */ -static NSString* _JRPrivate_EnumToString(NSArray *labelsAndValues, NSString *enumTypeName, int enumValue) { +static NSString* _JRPrivate_EnumToString(NSArray *labelsAndValues, NSString *enumTypeName, NSInteger enumValue) { NSString *result = [_JRPrivate_EnumByValue(labelsAndValues) objectForKey:[NSNumber numberWithInt:enumValue]]; if (!result) { result = [NSString stringWithFormat:@"", enumTypeName, enumValue]; @@ -148,7 +148,7 @@ static NSDictionary* ENUM_TYPENAME##ByLabel() { \ return _JRPrivate_EnumByLabel(labelsAndValues); \ } \ \ -static NSString* ENUM_TYPENAME##ToString(int enumValue) { \ +static NSString* ENUM_TYPENAME##ToString(NSInteger enumValue) { \ NSArray *labelsAndValues = _##ENUM_TYPENAME##LabelsAndValues(); \ NSString *enumTypeName = @"" #ENUM_TYPENAME; \ return _JRPrivate_EnumToString(labelsAndValues, enumTypeName, enumValue); \ From 4ed07979e37868d215b441dcb2d1906faca907cb Mon Sep 17 00:00:00 2001 From: Benedict Cohen Date: Tue, 3 Mar 2015 11:25:56 +0000 Subject: [PATCH 12/14] Fixed warning --- JREnum.h | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/JREnum.h b/JREnum.h index 8402d37..42ebd85 100644 --- a/JREnum.h +++ b/JREnum.h @@ -95,9 +95,10 @@ static NSDictionary* _JRPrivate_EnumByLabel(NSArray *labelsAndValues) { @return The label for enumValue. */ static NSString* _JRPrivate_EnumToString(NSArray *labelsAndValues, NSString *enumTypeName, NSInteger enumValue) { - NSString *result = [_JRPrivate_EnumByValue(labelsAndValues) objectForKey:[NSNumber numberWithInt:enumValue]]; + NSNumber *number = [NSNumber numberWithInteger:enumValue]; + NSString *result = [_JRPrivate_EnumByValue(labelsAndValues) objectForKey:number]; if (!result) { - result = [NSString stringWithFormat:@"", enumTypeName, enumValue]; + result = [NSString stringWithFormat:@"", enumTypeName, number]; } return result; } From 97b0c5b119041380350dfe53a6c8a14e599f4c4f Mon Sep 17 00:00:00 2001 From: Benedict Cohen Date: Tue, 3 Mar 2015 11:26:45 +0000 Subject: [PATCH 13/14] Fixed warning --- JREnum.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/JREnum.h b/JREnum.h index 42ebd85..2305064 100644 --- a/JREnum.h +++ b/JREnum.h @@ -46,7 +46,7 @@ static NSArray* _JRPrivate_ParseEnumLabelsAndValuesFromString(NSString *enumStri } nextDefaultValue = value + 1; [labelsAndValues addObject:label]; - [labelsAndValues addObject:[NSNumber numberWithInt:value]]; + [labelsAndValues addObject:[NSNumber numberWithInteger:value]]; } return labelsAndValues; } From ddc2d7b55eb63150ba067dcbc5ce378f65d0aa16 Mon Sep 17 00:00:00 2001 From: Benedict Cohen Date: Tue, 3 Mar 2015 11:59:31 +0000 Subject: [PATCH 14/14] - Added static - Added comment --- JREnum.h | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/JREnum.h b/JREnum.h index 2305064..a745f44 100644 --- a/JREnum.h +++ b/JREnum.h @@ -9,7 +9,7 @@ Parses enumString into an array of interleaved labels and keys. TODO: Document restrictions on key. The follow, for example, will have strange results: - 1. JREnumValue = NSNotFound + 1. JREnumValue = NSNotFound (NSNotFound is defined as a enum value. If it were `#define`d then it would work as we'd receive the post-processed value.) 2. JREnumNewValue = 0, JRValueOldEnum = JREnumNewValue, 3. ArfVoid = 0, Arf1, Arf2 = (Arf1 * (2 + ArfVoid)), It's possible to improve the function so that it can parse cases 2 and 3 but not case 1. @@ -135,7 +135,7 @@ typedef NS_ENUM(NSInteger, ENUM_TYPENAME) { \ \ \ static NSArray* _##ENUM_TYPENAME##LabelsAndValues() { \ - NSString *enumString = @"" #ENUM_CONSTANTS; \ + static NSString *enumString = @"" #ENUM_CONSTANTS; \ return _JRPrivate_ParseEnumLabelsAndValuesFromString(enumString); \ } \ \