- support typedefs of pointer types in treat_as

- fixed multi-line typedef declaration rejection

git-svn-id: http://cmock.svn.sourceforge.net/svnroot/cmock/trunk@179 bf332499-1b4d-0410-844d-d2d48d5cc64c
This commit is contained in:
mvandervoord
2010-07-19 14:02:42 +00:00
parent 7e0c3907b8
commit 840e38998b
4 changed files with 72 additions and 13 deletions
+5 -5
View File
@@ -69,11 +69,11 @@ class CMockHeaderParser
# enums, unions, structs, and typedefs can all contain things (e.g. function pointers) that parse like function prototypes, so yank them
# forward declared structs are removed before struct definitions so they don't mess up real thing later. we leave structs keywords in function prototypes
source.gsub!(/^[\w\s]*struct[^;\{\}\(\)]+;/m, '') # remove forward declared structs
source.gsub!(/^[\w\s]*(enum|union|struct)[\w\s]*\{[^\}]+\}[\w\s]*;/m, '') # remove struct definitions
source.gsub!(/(\W)(register|auto|static|restrict)(\W)/, '\1\3') # remove problem keywords
source.gsub!(/\s*=\s*['"a-zA-Z0-9_\.]+\s*/, '') # remove default value statements from argument lists
source.gsub!(/^(?:.*\W)?typedef\W.*/, '') # remove typedef statements
source.gsub!(/^[\w\s]*struct[^;\{\}\(\)]+;/m, '') # remove forward declared structs
source.gsub!(/^[\w\s]*(enum|union|struct|typepdef)[\w\s]*\{[^\}]+\}[\w\s\*\,]*;/m, '') # remove struct, union, and enum definitions and typedefs with braces
source.gsub!(/(\W)(register|auto|static|restrict)(\W)/, '\1\3') # remove problem keywords
source.gsub!(/\s*=\s*['"a-zA-Z0-9_\.]+\s*/, '') # remove default value statements from argument lists
source.gsub!(/^(?:[\w\s]*\W)?typedef\W.*/, '') # remove typedef statements
#scan for functions which return function pointers, because they are a pain
source.gsub!(/([\w\s\*]+)\(*\(\s*\*([\w\s\*]+)\s*\(([\w\s\*,]*)\)\)\s*\(([\w\s\*,]*)\)\)*/) do |m|
+6 -2
View File
@@ -33,8 +33,12 @@ class CMockUnityHelperParser
def map_C_types
c_types = {}
@config.treat_as.each_pair do |ctype, expecttype|
c_types[ctype.gsub(/\s+/,'_')] = "UNITY_TEST_ASSERT_EQUAL_#{expecttype}"
c_types[ctype.gsub(/\s+/,'_')+'*'] = "UNITY_TEST_ASSERT_EQUAL_#{expecttype}_ARRAY"
if (expecttype =~ /\*/)
c_types[ctype.gsub(/\s+/,'_')] = "UNITY_TEST_ASSERT_EQUAL_#{expecttype.gsub(/\*/,'')}_ARRAY"
else
c_types[ctype.gsub(/\s+/,'_')] = "UNITY_TEST_ASSERT_EQUAL_#{expecttype}"
c_types[ctype.gsub(/\s+/,'_')+'*'] = "UNITY_TEST_ASSERT_EQUAL_#{expecttype}_ARRAY"
end
end
c_types
end
@@ -2,6 +2,8 @@
:cmock:
:plugins:
- # none
:treat_as:
INT_PTR: INT*
:systest:
:types: |
@@ -9,6 +11,7 @@
int x;
int y;
} POINT_T;
typedef int* INT_PTR;
:mockable: |
void foo(POINT_T* a);
@@ -16,12 +19,14 @@
void fooa(POINT_T a[]);
void foos(const char *a);
const char* bars(void);
INT_PTR zoink(INT_PTR a);
:source:
:header: |
void function_a(void);
void function_b(void);
void function_c(void);
int function_d(void);
:code: |
void function_a(void)
@@ -37,6 +42,12 @@
foos(bars());
}
int function_d(void) {
int i = 456;
INT_PTR ptr = (INT_PTR)(&i);
return (int)(*(zoink(ptr)));
}
:tests:
:common: |
void setUp(void) {}
@@ -162,6 +173,36 @@
function_c();
}
- :pass: TRUE
:should: 'handle handle typedefs that ARE pointers by using treat_as'
:code: |
test()
{
int e = 456;
int r = 789;
INT_PTR ptr_e = (INT_PTR)(&e);
INT_PTR ptr_r = (INT_PTR)(&r);
zoink_ExpectAndReturn(ptr_e, ptr_r);
TEST_ASSERT_EQUAL(r, function_d());
}
- :pass: FALSE
:should: 'handle handle typedefs that ARE pointers by using treat_as and catch failures'
:code: |
test()
{
int e = 457;
int r = 789;
INT_PTR ptr_e = (INT_PTR)(&e);
INT_PTR ptr_r = (INT_PTR)(&r);
zoink_ExpectAndReturn(ptr_e, ptr_r);
TEST_ASSERT_EQUAL(r, function_d());
}
...
+20 -6
View File
@@ -140,12 +140,25 @@ class CMockHeaderParserTest < Test::Unit::TestCase
should "remove typedef statements" do
source =
"typedef uint32 (unsigned int);\n" +
"whack me! typedef int INT;\n" +
"const typedef int INT;\n" +
"int notatypedef;\n" +
"int typedef_isnt_me;\n" +
" typedef who cares what really comes here \\\n" + # exercise multiline typedef
" continuation;\n" +
"this should remain!\n"
"this should remain!;\n" +
"typedef blah bleh;\n" +
"typedef struct shell_command_struct {\n" +
" char_ptr COMMAND;\n" +
" int_32 (*SHELL_FUNC)(int_32 argc);\n" +
"} SHELL_COMMAND_STRUCT, * SHELL_COMMAND_PTR;\n" +
"typedef struct shell_command_struct {\n" +
" char_ptr COMMAND;\n" +
" int_32 (*SHELL_FUNC)(int_32 argc, char_ptr argv[]);\n" +
"} SHELL_COMMAND_STRUCT, * SHELL_COMMAND_PTR;\n" +
"typedef struct shell_command_struct {\n" +
" char_ptr COMMAND;\n" +
" int_32 (*SHELL_FUNC)(int_32 argc);\n" +
"};\n"
expected =
[
@@ -787,7 +800,7 @@ class CMockHeaderParserTest < Test::Unit::TestCase
end
should "handle arrays and treat them as pointers" do
source = "void KeyOperated(CUSTOM_TYPE thing1[], int thing2 [ ], char thing3 [][2 ][ 3])"
source = "void KeyOperated(CUSTOM_TYPE thing1[], int thing2 [ ], char thing3 [][2 ][ 3], int* thing4[4])"
expected = [{:var_arg=>nil,
:return=>{ :type => "void",
:name => 'cmock_to_return',
@@ -801,10 +814,11 @@ class CMockHeaderParserTest < Test::Unit::TestCase
:contains_ptr? => true,
:args=>[ {:type=>"CUSTOM_TYPE*", :name=>"thing1", :ptr? => true, :const? => false},
{:type=>"int*", :name=>"thing2", :ptr? => true, :const? => false},
{:type=>"char*", :name=>"thing3", :ptr? => false, :const? => false} #THIS one will likely change in the future when we improve multidimensional array support
{:type=>"char*", :name=>"thing3", :ptr? => false, :const? => false}, #THIS one will likely change in the future when we improve multidimensional array support
{:type=>"int**", :name=>"thing4", :ptr? => true, :const? => false} #THIS one will likely change in the future when we improve multidimensional array support
],
:args_string=>"CUSTOM_TYPE* thing1, int* thing2, char* thing3",
:args_call=>"thing1, thing2, thing3" }]
:args_string=>"CUSTOM_TYPE* thing1, int* thing2, char* thing3, int** thing4",
:args_call=>"thing1, thing2, thing3, thing4" }]
result = @parser.parse("module", source)
assert_equal(expected, result[:functions])
end