├── Makefile ├── Makefile.in ├── README.md ├── configure ├── configure.ac ├── depends.d ├── include ├── bitfield.h ├── block_field.h ├── choice_field.h ├── command_parser.h ├── compound_field.h ├── const_value_node.h ├── endianness.h ├── exceptions.h ├── executer.h ├── field.h ├── field_filler.h ├── field_impl.h ├── field_mapper.h ├── field_serializer.h ├── function_nodes.h ├── function_value_filler.h ├── functions │ ├── constraints.h │ ├── crc.h │ ├── hashing.h │ ├── misc.h │ └── random.h ├── generation_context.h ├── multiptr_destructor.h ├── parser │ ├── nodes.h │ ├── syntax.h │ ├── syntax.tab.h │ └── syntax_parser.h ├── template_field.h ├── topological_sorter.h ├── unary_field_function.h ├── utils.h ├── value_filler.h ├── value_node.h └── variable_block_field.h ├── m4 └── ax_cxx_compile_stdcxx_11.m4 ├── parser ├── grammar.y └── syntax.lex ├── src ├── bitfield.cpp ├── choice_field.cpp ├── command_parser.cpp ├── compound_field.cpp ├── const_value_node.cpp ├── exceptions.cpp ├── executer.cpp ├── field.cpp ├── field_impl.cpp ├── field_mapper.cpp ├── field_serializer.cpp ├── function_value_filler.cpp ├── functions │ ├── constraints.cpp │ ├── crc.cpp │ ├── hashing.cpp │ └── random.cpp ├── generation_context.cpp ├── main.cpp ├── parser │ ├── grammar.cpp │ ├── nodes.cpp │ ├── syntax.cpp │ └── syntax_parser.cpp ├── template_field.cpp ├── topological_sorter.cpp ├── value_filler.cpp └── variable_block_field.cpp └── templates ├── jpeg ├── mp3 └── png /Makefile: -------------------------------------------------------------------------------- 1 | CXX=g++ 2 | CP=cp 3 | MV=mv 4 | CXXFLAGS= -c -Wall -g -O2 -std=c++11 -DFUZZER_VERSION=0.1 5 | LEX=flex 6 | YACC=bison -y 7 | INCLUDE = -Iinclude 8 | LDFLAGS= -lpthread -lcrypto 9 | RM=rm 10 | SOURCES= $(wildcard src/*.cpp src/functions/*.cpp) src/parser/syntax_parser.cpp src/parser/nodes.cpp 11 | OBJECTS=$(SOURCES:.cpp=.o) src/parser/grammar.o src/parser/syntax.o 12 | DEPS = $(SOURCES:.cpp=.d) 13 | 14 | EXECUTABLE=sloth 15 | 16 | all: $(SOURCES) $(EXECUTABLE) 17 | 18 | compile: $(OBJECTS) 19 | 20 | recompile: clean all 21 | 22 | depends: $(SOURCES) 23 | rm -f ./depends.d 24 | make do_make_deps 25 | 26 | do_make_deps: $(DEPS) 27 | 28 | %.d : %.cpp 29 | $(CXX) $(CXXFLAGS) $(INCLUDE) -MG -MM -MP -MT"$(<:.cpp=.o)" $< >> depends.d 30 | 31 | install: 32 | $(CP) $(EXECUTABLE) /usr/bin/ 33 | uninstall: 34 | $(RM) /usr/bin/$(EXECUTABLE) 35 | 36 | $(EXECUTABLE): $(OBJECTS) 37 | $(CXX) $(OBJECTS) $(LDFLAGS) -o $@ 38 | 39 | .cpp.o: 40 | $(CXX) $(CXXFLAGS) $(INCLUDE) $< -o $@ 41 | 42 | src/parser/grammar.o: parser/grammar.y parser/syntax.lex include/parser/nodes.h 43 | $(YACC) -d -o parser/grammar-output parser/grammar.y 44 | $(MV) parser/grammar-output src/parser/grammar.cpp 45 | $(MV) parser/grammar-output.h include/parser/syntax.tab.h 46 | $(CXX) $(CXXFLAGS) $(INCLUDE) src/parser/grammar.cpp -o src/parser/grammar.o 47 | 48 | src/parser/syntax.o: parser/syntax.lex src/parser/grammar.o 49 | $(LEX) -o src/parser/syntax.cpp parser/syntax.lex 50 | $(CXX) $(CXXFLAGS) $(INCLUDE) src/parser/syntax.cpp -o src/parser/syntax.o 51 | 52 | clean: 53 | rm $(OBJECTS) $(EXECUTABLE) 54 | 55 | -include depends.d 56 | -------------------------------------------------------------------------------- /Makefile.in: -------------------------------------------------------------------------------- 1 | CXX=@CXX@ 2 | CP=cp 3 | MV=mv 4 | CXXFLAGS= -c -Wall @CXXFLAGS@ -DFUZZER_VERSION=@PACKAGE_VERSION@ 5 | LEX=@LEX@ 6 | YACC=@YACC@ 7 | INCLUDE = -Iinclude 8 | LDFLAGS= -lpthread -lcrypto @LDFLAGS@ 9 | RM=rm 10 | SOURCES= $(wildcard src/*.cpp src/functions/*.cpp) src/parser/syntax_parser.cpp src/parser/nodes.cpp 11 | OBJECTS=$(SOURCES:.cpp=.o) src/parser/grammar.o src/parser/syntax.o 12 | DEPS = $(SOURCES:.cpp=.d) 13 | 14 | EXECUTABLE=sloth 15 | 16 | all: $(SOURCES) $(EXECUTABLE) 17 | 18 | compile: $(OBJECTS) 19 | 20 | recompile: clean all 21 | 22 | depends: $(SOURCES) 23 | rm -f ./depends.d 24 | make do_make_deps 25 | 26 | do_make_deps: $(DEPS) 27 | 28 | %.d : %.cpp 29 | $(CXX) $(CXXFLAGS) $(INCLUDE) -MG -MM -MP -MT"$(<:.cpp=.o)" $< >> depends.d 30 | 31 | install: 32 | $(CP) $(EXECUTABLE) /usr/bin/ 33 | uninstall: 34 | $(RM) /usr/bin/$(EXECUTABLE) 35 | 36 | $(EXECUTABLE): $(OBJECTS) 37 | $(CXX) $(OBJECTS) $(LDFLAGS) -o $@ 38 | 39 | .cpp.o: 40 | $(CXX) $(CXXFLAGS) $(INCLUDE) $< -o $@ 41 | 42 | src/parser/grammar.o: parser/grammar.y parser/syntax.lex include/parser/nodes.h 43 | $(YACC) -d -o parser/grammar-output parser/grammar.y 44 | $(MV) parser/grammar-output src/parser/grammar.cpp 45 | $(MV) parser/grammar-output.h include/parser/syntax.tab.h 46 | $(CXX) $(CXXFLAGS) $(INCLUDE) src/parser/grammar.cpp -o src/parser/grammar.o 47 | 48 | src/parser/syntax.o: parser/syntax.lex src/parser/grammar.o 49 | $(LEX) -o src/parser/syntax.cpp parser/syntax.lex 50 | $(CXX) $(CXXFLAGS) $(INCLUDE) src/parser/syntax.cpp -o src/parser/syntax.o 51 | 52 | clean: 53 | rm $(OBJECTS) $(EXECUTABLE) 54 | 55 | -include depends.d 56 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | sloth 2 | ===== 3 | 4 | sloth is a smart file fuzzer. 5 | 6 | ## Why is it a smart fuzzer? ## 7 | 8 | The files generated when fuzzing are not just random data. You must 9 | provide a template file, which describes the structure of the generated 10 | files. 11 | 12 | ## How is it different from other smart fuzzers? ## 13 | 14 | Every smart fuzzer I've found uses either XML or some programming 15 | language script to describe the structure of the fuzzed files. Using 16 | XML is tedious, you must provide starting tags, ending tags, named 17 | attributes, etc. Using actual programming language scripts forces the 18 | user to learn both the structure definition directives and the 19 | programming language itself. 20 | 21 | *sloth* uses its own syntax to represent the file structure. For example, 22 | this template file provides the structure for a basic jpeg file: 23 | 24 | ``` 25 | templates { 26 | segment { 27 | # the first byte will be 0xff 28 | block<1> = 0xff; 29 | 30 | # the next byte will be randomized 31 | block<1>; 32 | 33 | # the next 2-byte field will contain the size of the data field 34 | block<2> = size(data); 35 | 36 | # the data field will contain 0 to 2000 random bytes 37 | var_block<0, 2000> data; 38 | }; 39 | }; 40 | 41 | # JPG magic number 42 | str_block = "\xff\xd8\xff\xe0"; 43 | 44 | block<2> = 16; 45 | 46 | # JFIF identifier 47 | str_block = "JFIF\x00\x01\x02"; 48 | 49 | # units 50 | block<8> = 0; 51 | 52 | # 0 to 200 segments, as defined above 53 | template; 54 | ``` 55 | 56 | In order to use sloth, you just need to understand a few primitives 57 | which are used to define blocks. 58 | 59 | ## Compilation ## 60 | 61 | *sloth* requires the following libraries/applications/features: 62 | 63 | * libcrypto 64 | * flex 65 | * bison 66 | * A C++ compiler that has nice support for C++11 features(gcc >= 4.7 for example) 67 | 68 | In order to compile, just do the usual: 69 | 70 | ```Shell 71 | ./configure 72 | make 73 | ``` 74 | 75 | ## Running sloth ## 76 | 77 | In order to start test some application, just execute sloth indicating 78 | the template file to use: 79 | 80 | ```Shell 81 | # just as an example 82 | ./sloth -t /tmp/some_template_file some_application some_app_param1 83 | 84 | # fuzz mpg123, for example 85 | ./sloth -t templates/mp3 mpg123 86 | 87 | # you can also use parameters, "-2" here is a mpg123 parameter 88 | ./sloth -t templates/mp3 mpg123 -2 89 | 90 | # same as above, {%} indicates the place in which the name of the file 91 | # will be replaced. By default it's replaced at the end of the command 92 | ./sloth -t templates/mp3 mpg123 -2 {%} 93 | ``` 94 | 95 | If at any point, the application being tested crashes, the file that 96 | made it crash will be moved to /tmp/fuzzer-NUMBER, where NUMBER will 97 | be 0 initially, and incremented each time a file makes the application 98 | crash. If you want to provide a different base name 99 | (here you'd replace the /tmp/fuzzer-), provide the -d parameter: 100 | 101 | ```Shell 102 | ./sloth -t something -d /home/something/persistent_dir/crash-file application 103 | ``` 104 | 105 | Some applications might require the name of the file to have a specific 106 | extension. By default, the generated file will be named /tmp/sloth-file. 107 | If you want to use another name, use the -o parameter: 108 | 109 | ```Shell 110 | ./sloth -t something -o /dev/shm/sloth.jpg convert {%} /dev/shm/sloth.png 111 | ``` 112 | 113 | ## Template file definition ## 114 | 115 | sloth uses its own syntax to allow users to represent template files 116 | that will be used when fuzzing. While fuzzing, every generated file 117 | will be constructed using the structure provided in the template file. 118 | 119 | The templates' layout is basically a list of blocks. There are different 120 | kind of blocks, each of them provides different features: 121 | 122 | ### block ### 123 | 124 | blocks can be used to represent fields of static size. When you declare 125 | a block, you need to provide the size, and optionally a value. If you 126 | don't provide any value, its contents shall be randomized: 127 | 128 | ``` 129 | # defines a 4-bytes block, the contents will be random 130 | block<4>; 131 | 132 | # using a specific value 133 | block<2> = 15; 134 | 135 | block<4> = 0xdeadbeef; 136 | 137 | # give it a name, and use some function over it 138 | block<50> md5_input; 139 | 140 | # will contain the MD5 hash of the contents of md5_input 141 | block<16> = md5(md5_input); 142 | 143 | # expressions are allowed as well 144 | block<1> foo; 145 | 146 | block<4> = foo * 15 + 1; 147 | 148 | # you use a string as well 149 | block<7> = "HELLO\xde\xad"; 150 | ``` 151 | 152 | ### var_block ### 153 | 154 | var_blocks contain a variable amount of data. The minimum and maximum 155 | amount of data must be provided on their definition: 156 | 157 | ``` 158 | # will contain between 0 and 5 bytes 159 | var_block<0, 5>; 160 | 161 | # 5 to 10 bytes filled with 0 162 | var_block<5, 10> foo = 0; 163 | 164 | # use the size of the field 165 | block<4> = size(foo); 166 | ``` 167 | 168 | ### str_block ### 169 | 170 | str_blocks are just blocks that must be initialized with a string value. 171 | The length of the block will be equal to the length of the string: 172 | 173 | ``` 174 | # will be a 4 byte block 175 | str_block = "beef"; 176 | 177 | # 6 bytes 178 | str_block = "hi\xff\x08ho"; 179 | ``` 180 | 181 | ### multi_bit and bitfield ### 182 | 183 | multi_bit blocks are just wrappers over several bitfields. bitfields 184 | represent fields which contain bits instead of bytes. bitfields can be 185 | assigned a value or expression: 186 | 187 | ``` 188 | # wrapper over the inner bitfields 189 | multi_bit { 190 | bitfield<2> = 0; 191 | bitfield<4> = 0xff; 192 | 193 | # randomized 194 | bitfield<2>; 195 | }; 196 | 197 | # named as well 198 | multi_bit something { 199 | bitfield<24>; 200 | bitfield<8> = 0xfe; 201 | }; 202 | 203 | block<16> = md5(something); 204 | ``` 205 | 206 | ### multi_block ### 207 | 208 | multi_blocks are very similar to multi_bit fields. The main difference 209 | is that they hold regular fields, rather than only bitfields. 210 | 211 | ``` 212 | # some fields 213 | multi_block my_big_block { 214 | block<4>; 215 | block<1> = 0; 216 | multi_bit { 217 | bitfield<4>; 218 | bitfield<4> = 5; 219 | }; 220 | }; 221 | ``` 222 | 223 | 224 | ### templates ### 225 | 226 | template blocks are very useful when you need to repetedly use a certain 227 | structure. templates are defined at the beginning of the file, and can 228 | be instantiated at any point in them: 229 | 230 | ``` 231 | # our file begins with this definitions 232 | templates { 233 | # foo is a template 234 | foo { 235 | block<4> bar; 236 | block<16> = md5(bar); 237 | }; 238 | }; 239 | 240 | # instantiate our template 241 | template; 242 | 243 | # instantiate 5 foos 244 | template; 245 | 246 | # instantiate between 6 and 8 foos 247 | template bleh; 248 | 249 | # will hold 6, 7 or 8 depending on how many fields does bleh contain 250 | block<1> = count(bleh); 251 | ``` 252 | 253 | ### choice ### 254 | 255 | choices are fields that contain several fields, but only one of them 256 | will be used in each file generation: 257 | 258 | ``` 259 | # can contain either 2 or 4 random bytes 260 | choice { 261 | block<4>; 262 | block<2>; 263 | }; 264 | ``` 265 | 266 | ### functions ### 267 | 268 | There are some functions defined which allow you to initialize your 269 | field values with some value that depends on other fields' values: 270 | 271 | ``` 272 | # some random block 273 | block<50> input; 274 | 275 | # crc 276 | block<4> = crc32(input); 277 | 278 | # md5 279 | block<16> = md5(input); 280 | 281 | # sha1 282 | block<20> = sha1(input); 283 | 284 | # always 50 285 | block<2> = size(input); 286 | ``` 287 | -------------------------------------------------------------------------------- /configure.ac: -------------------------------------------------------------------------------- 1 | AC_INIT([sloth], [0.1], [matias.fontanini@gmail.com], [sloth], [http://slothfuzzer.sourceforge.net]) 2 | 3 | m4_include([m4/ax_cxx_compile_stdcxx_11.m4]) 4 | AC_PROG_CXX() 5 | AC_LANG(C++) 6 | 7 | AC_PROG_LEX 8 | if test $LEX == ":" 9 | then 10 | AC_MSG_ERROR(***flex is not installed***) 11 | fi 12 | 13 | AC_PROG_YACC 14 | if test $YACC == "yacc" 15 | then 16 | AC_MSG_ERROR(***bison is not installed***) 17 | fi 18 | 19 | AC_CHECK_LIB(crypto, MD5, [], [AC_MSG_ERROR(***libcrypto is not installed***)]) 20 | 21 | 22 | AX_CXX_COMPILE_STDCXX_11(noext) 23 | 24 | # Check headers 25 | 26 | AC_CHECK_HEADERS([openssl/md5.h]) 27 | 28 | AC_OUTPUT(Makefile) 29 | -------------------------------------------------------------------------------- /include/bitfield.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #ifndef FUZZER_BITFIELD_H 31 | #define FUZZER_BITFIELD_H 32 | 33 | #include 34 | #include 35 | #include "field_impl.h" 36 | #include "field.h" 37 | #include "block_field.h" 38 | #include "exceptions.h" 39 | 40 | class compound_bitfield_impl : public clonable_field_impl { 41 | public: 42 | template 43 | compound_bitfield_impl(InputIterator start, InputIterator end) 44 | : fields(start, end) 45 | { 46 | for(const auto &f : fields) 47 | data.resize(data.size() + f.size()); 48 | } 49 | 50 | void set(size_t index, value_type value); 51 | value_type get(size_t index) const; 52 | size_t size() const; 53 | size_t field_count() const; 54 | void prepare(generation_context &); 55 | 56 | dependents_type dependent_fields() const; 57 | void accept_visitor(const visitor_type& visitor) const; 58 | buffer_iterator fill_from_buffer(buffer_iterator start, buffer_iterator end); 59 | private: 60 | typedef std::vector fields_type; 61 | 62 | fields_type fields; 63 | std::vector data; 64 | }; 65 | 66 | typedef generic_block_field_impl> bitfield_impl; 67 | 68 | template<> 69 | inline void generic_block_field_impl>::set_value(int64_t value) 70 | { 71 | for(auto iter = data.rbegin(); iter != data.rend(); ++iter) { 72 | *iter = value & 1; 73 | value >>= 1; 74 | } 75 | if(value > 0) 76 | throw value_too_large(); 77 | } 78 | 79 | template<> 80 | inline int64_t generic_block_field_impl>::get_value() const 81 | { 82 | uint64_t value{}; 83 | for(auto iter = data.rbegin(); iter != data.rend(); ++iter) { 84 | value = (value << 1) | static_cast(*iter); 85 | } 86 | return value; 87 | } 88 | 89 | #endif 90 | -------------------------------------------------------------------------------- /include/block_field.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #ifndef FUZZER_BLOCK_FIELD_H 31 | #define FUZZER_BLOCK_FIELD_H 32 | 33 | #include 34 | #include "field_impl.h" 35 | #include "exceptions.h" 36 | 37 | template 38 | class generic_block_field_impl : public clonable_field_impl> { 39 | public: 40 | typedef Container container_type; 41 | typedef field_impl::buffer_iterator buffer_iterator; 42 | using field_impl::get_value; 43 | 44 | generic_block_field_impl(size_t data_size) 45 | : data(data_size) 46 | { 47 | 48 | } 49 | 50 | void set(size_t index, field_impl::value_type value) 51 | { 52 | data[index] = value; 53 | } 54 | 55 | field_impl::value_type get(size_t index) const 56 | { 57 | return data[index]; 58 | } 59 | 60 | size_t size() const 61 | { 62 | return data.size(); 63 | } 64 | 65 | void set_value(int64_t value) 66 | { 67 | field_impl::set_value(value); 68 | } 69 | 70 | int64_t get_value() const 71 | { 72 | return field_impl::get_value(); 73 | } 74 | 75 | buffer_iterator fill_from_buffer(buffer_iterator start, buffer_iterator end) 76 | { 77 | if(std::distance(start, end) < static_cast(data.size())) 78 | throw not_enough_data(); 79 | std::copy(start, start + data.size(), data.begin()); 80 | return start + data.size(); 81 | } 82 | private: 83 | container_type data; 84 | }; 85 | 86 | typedef generic_block_field_impl> block_field_impl; 87 | 88 | #endif // FUZZER_BLOCK_FIELD_H 89 | -------------------------------------------------------------------------------- /include/choice_field.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #ifndef FUZZER_CHOICE_FIELD_H 31 | #define FUZZER_CHOICE_FIELD_H 32 | 33 | #include 34 | #include "field.h" 35 | #include "field_impl.h" 36 | 37 | class choice_field_impl : public clonable_field_impl { 38 | public: 39 | template 40 | choice_field_impl(InputIterator start, InputIterator end) 41 | : choices(start, end), current_choice(nullptr) 42 | { 43 | for(const auto &i : choices) { 44 | auto &&deps = i.dependent_fields(); 45 | dependents.insert( 46 | dependents.end(), 47 | deps.begin(), 48 | deps.end() 49 | ); 50 | } 51 | } 52 | 53 | void set(size_t index, value_type value); 54 | value_type get(size_t index) const; 55 | size_t size() const; 56 | void prepare(generation_context &ctx); 57 | dependents_type dependent_fields() const; 58 | private: 59 | std::vector choices; 60 | dependents_type dependents; 61 | field *current_choice; 62 | }; 63 | 64 | #endif // FUZZER_CHOICE_FIELD_H 65 | -------------------------------------------------------------------------------- /include/command_parser.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #ifndef FUZZER_COMMAND_PARSER_H 31 | #define FUZZER_COMMAND_PARSER_H 32 | 33 | #include 34 | #include 35 | #include 36 | 37 | class command_parser { 38 | public: 39 | typedef std::vector arguments_type; 40 | 41 | command_parser(const std::string &cmd); 42 | 43 | std::tuple generate_template(const std::string &file_name) const; 44 | private: 45 | std::tuple split_cmd(const std::string &cmd); 46 | 47 | std::string application; 48 | arguments_type arguments; 49 | size_t replacement_index; 50 | }; 51 | 52 | #endif // FUZZER_COMMAND_PARSER_H 53 | -------------------------------------------------------------------------------- /include/compound_field.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #ifndef FUZZER_COMPOUND_FIELD_H 31 | #define FUZZER_COMPOUND_FIELD_H 32 | 33 | #include 34 | #include 35 | #include 36 | #include "field_impl.h" 37 | #include "field.h" 38 | 39 | class compound_field_impl : public clonable_field_impl { 40 | public: 41 | template 42 | compound_field_impl(InputIterator start, InputIterator end) 43 | : fields(start, end), last_iterator(indexes.end()), total_size(0) 44 | { 45 | 46 | } 47 | 48 | compound_field_impl(); 49 | compound_field_impl(const compound_field_impl &f); 50 | compound_field_impl(compound_field_impl&&) = default; 51 | compound_field_impl& operator=(compound_field_impl f); 52 | 53 | void prepare(generation_context &); 54 | void set(size_t index, value_type value); 55 | value_type get(size_t index) const; 56 | size_t size() const; 57 | size_t field_count() const; 58 | void accept_visitor(const visitor_type& visitor) const; 59 | buffer_iterator fill_from_buffer(buffer_iterator start, buffer_iterator end); 60 | 61 | dependents_type dependent_fields() const; 62 | 63 | friend void swap(compound_field_impl &lhs, compound_field_impl &rhs); 64 | protected: 65 | void clear_children(); 66 | void add_field(field child); 67 | private: 68 | typedef std::vector fields_type; 69 | typedef std::map indexes_type; 70 | 71 | indexes_type::const_iterator find_index(size_t index) const; 72 | 73 | fields_type fields; 74 | indexes_type indexes; 75 | mutable indexes_type::const_iterator last_iterator; 76 | size_t total_size; 77 | }; 78 | 79 | #endif // FUZZER_COMPOUND_FIELD_H 80 | -------------------------------------------------------------------------------- /include/const_value_node.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #ifndef FUZZER_CONST_VALUE_NODE_H 31 | #define FUZZER_CONST_VALUE_NODE_H 32 | 33 | #include 34 | #include 35 | #include "value_node.h" 36 | #include "field_filler.h" 37 | 38 | class const_value_node : public value_node { 39 | public: 40 | const_value_node(double value); 41 | double eval(generation_context &ctx); 42 | private: 43 | double value; 44 | }; 45 | 46 | class const_string_node : public field_filler { 47 | public: 48 | const_string_node(std::string value); 49 | void fill(field &f, generation_context &ctx); 50 | private: 51 | std::string value; 52 | }; 53 | 54 | #endif // FUZZER_CONST_VALUE_NODE_H 55 | -------------------------------------------------------------------------------- /include/endianness.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #ifndef FUZZER_ENDIANNESS_H 31 | #define FUZZER_ENDIANNESS_H 32 | 33 | #include 34 | 35 | #if defined(__unix__) || (defined(__APPLE__) && defined(__MACH__)) 36 | #include 37 | #endif 38 | 39 | #if defined(__APPLE__) 40 | #include 41 | #define FUZZER_IS_LITTLE_ENDIAN (BYTE_ORDER == LITTLE_ENDIAN) 42 | #define FUZZER_IS_BIG_ENDIAN (BYTE_ORDER == BIG_ENDIAN) 43 | #elif defined(BSD) 44 | #include 45 | #define FUZZER_IS_LITTLE_ENDIAN (_BYTE_ORDER == _LITTLE_ENDIAN) 46 | #define FUZZER_IS_BIG_ENDIAN (_BYTE_ORDER == _BIG_ENDIAN) 47 | #elif defined(WIN32) 48 | // Assume windows == little endian. fixme later 49 | #define FUZZER_IS_LITTLE_ENDIAN 1 50 | #define FUZZER_IS_BIG_ENDIAN 0 51 | #else 52 | #include 53 | #define FUZZER_IS_LITTLE_ENDIAN (__BYTE_ORDER == __LITTLE_ENDIAN) 54 | #define FUZZER_IS_BIG_ENDIAN (__BYTE_ORDER == __BIG_ENDIAN) 55 | #endif 56 | 57 | 58 | 59 | namespace Endian { 60 | 61 | inline uint16_t do_change_endian(uint16_t data) { 62 | return ((data & 0xff00) >> 8) | ((data & 0x00ff) << 8); 63 | } 64 | 65 | inline uint32_t do_change_endian(uint32_t data) { 66 | return (((data & 0xff000000) >> 24) | ((data & 0x00ff0000) >> 8) | 67 | ((data & 0x0000ff00) << 8) | ((data & 0x000000ff) << 24)); 68 | } 69 | 70 | inline uint64_t do_change_endian(uint64_t data) { 71 | return (((uint64_t)(do_change_endian((uint32_t)((data << 32) >> 32))) << 32) | 72 | (do_change_endian(((uint32_t)(data >> 32))))); 73 | } 74 | 75 | // Helpers to convert 76 | template 77 | struct conversion_dispatch_helper { 78 | static T dispatch(T data) { 79 | return do_change_endian(data); 80 | } 81 | }; 82 | 83 | 84 | template 85 | struct conversion_dispatcher; 86 | 87 | template<> 88 | struct conversion_dispatcher 89 | : public conversion_dispatch_helper 90 | { }; 91 | 92 | template<> 93 | struct conversion_dispatcher 94 | : public conversion_dispatch_helper 95 | { }; 96 | 97 | template<> 98 | struct conversion_dispatcher 99 | : public conversion_dispatch_helper 100 | { }; 101 | 102 | template 103 | inline T change_endian(T data) { 104 | return conversion_dispatcher::dispatch(data); 105 | } 106 | 107 | #if FUZZER_IS_LITTLE_ENDIAN 108 | template 109 | inline T host_to_be(T data) { 110 | return change_endian(data); 111 | } 112 | 113 | template 114 | inline T host_to_le(T data) { 115 | return data; 116 | } 117 | 118 | template 119 | inline T be_to_host(T data) { 120 | return change_endian(data); 121 | } 122 | 123 | template 124 | inline T le_to_host(T data) { 125 | return data; 126 | } 127 | #elif FUZZER_IS_BIG_ENDIAN 128 | template 129 | inline T host_to_be(T data) { 130 | return data; 131 | } 132 | 133 | template 134 | inline T host_to_le(T data) { 135 | return change_endian(data); 136 | } 137 | 138 | template 139 | inline T be_to_host(T data) { 140 | return data; 141 | } 142 | 143 | template 144 | inline T le_to_host(T data) { 145 | return change_endian(data); 146 | } 147 | #endif 148 | } // namespace Endian 149 | 150 | #endif // FUZZER_ENDIANNESS_H 151 | -------------------------------------------------------------------------------- /include/exceptions.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #ifndef FUZZER_EXCEPTIONS_H 31 | #define FUZZER_EXCEPTIONS_H 32 | 33 | #include 34 | 35 | class invalid_field_size : public std::exception { 36 | public: 37 | const char *what() const throw(); 38 | }; 39 | 40 | class not_enough_data : public std::exception { 41 | public: 42 | const char *what() const throw(); 43 | }; 44 | 45 | class dependency_loop_error : public std::exception { 46 | public: 47 | const char *what() const throw(); 48 | }; 49 | 50 | class field_cant_be_used_in_response : public std::exception { 51 | public: 52 | const char *what() const throw(); 53 | }; 54 | 55 | class parse_error : public std::exception { 56 | public: 57 | const char *what() const throw(); 58 | }; 59 | 60 | class unprepared_field : public std::exception { 61 | public: 62 | const char *what() const throw(); 63 | }; 64 | 65 | class file_open_exception : public std::exception { 66 | public: 67 | const char *what() const throw(); 68 | }; 69 | 70 | class not_implemented : public std::exception { 71 | public: 72 | const char *what() const throw(); 73 | }; 74 | 75 | class constraint_too_soft : public std::exception { 76 | public: 77 | const char *what() const throw(); 78 | }; 79 | 80 | class no_constraints : public std::exception { 81 | public: 82 | const char *what() const throw(); 83 | }; 84 | 85 | class too_many_constraints : public std::exception { 86 | public: 87 | const char *what() const throw(); 88 | }; 89 | 90 | class value_too_large : public std::exception { 91 | public: 92 | const char *what() const throw(); 93 | }; 94 | 95 | class semantic_exception : public std::runtime_error { 96 | public: 97 | semantic_exception(size_t line, const std::string &str); 98 | }; 99 | 100 | class execution_exception : public std::runtime_error { 101 | public: 102 | execution_exception(const std::string &str); 103 | }; 104 | 105 | class ast_field_too_small : public semantic_exception { 106 | public: 107 | ast_field_too_small(size_t line, const std::string &node, const std::string &content); 108 | }; 109 | 110 | class incorrect_ast_field_size : public semantic_exception { 111 | public: 112 | incorrect_ast_field_size(size_t line, const std::string &node, size_t expected); 113 | }; 114 | 115 | class cant_deduct_field_type : public semantic_exception { 116 | public: 117 | cant_deduct_field_type(size_t line, const std::string &node); 118 | }; 119 | 120 | #endif // FUZZER_EXCEPTIONS_H 121 | -------------------------------------------------------------------------------- /include/executer.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #ifndef FUZZER_EXECUTER_H 31 | #define FUZZER_EXECUTER_H 32 | 33 | #include 34 | #include 35 | #include 36 | #include 37 | #include "command_parser.h" 38 | #include "exceptions.h" 39 | 40 | class field; 41 | 42 | class executer { 43 | public: 44 | enum class exec_status { 45 | success, 46 | failed, 47 | killed_by_signal 48 | }; 49 | executer(const std::string &cmd); 50 | 51 | template 52 | exec_status execute(ForwardIterator start, ForwardIterator end, const std::string &output_file) 53 | { 54 | std::ofstream output(output_file, std::ios::binary); 55 | if(!output) 56 | throw file_open_exception(); 57 | std::for_each(start, end, [&](uint8_t i) { output << i; }); 58 | output.close(); 59 | return do_execute(output_file); 60 | } 61 | private: 62 | exec_status do_execute(const std::string &file); 63 | 64 | command_parser cmd_template; 65 | }; 66 | 67 | #endif // FUZZER_EXECUTER_H 68 | -------------------------------------------------------------------------------- /include/field.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #ifndef FUZZER_FIELD_H 31 | #define FUZZER_FIELD_H 32 | 33 | #include 34 | #include 35 | #include 36 | #include 37 | #include 38 | #include 39 | #include 40 | #include "utils.h" 41 | #include "field_impl.h" 42 | #include "field_filler.h" 43 | 44 | template 45 | class field_iterator; 46 | 47 | template 48 | class dereference_helper; 49 | 50 | class field_mapper; 51 | class generation_context; 52 | 53 | class field { 54 | public: 55 | typedef field_impl::identifier_type identifier_type; 56 | typedef field_impl::value_type value_type; 57 | typedef field_impl::visitor_type visitor_type; 58 | typedef field_iterator iterator; 59 | typedef field_iterator const_iterator; 60 | typedef std::unique_ptr unique_impl; 61 | typedef std::shared_ptr filler_type; 62 | typedef field_impl::dependents_type dependents_type; 63 | typedef field_impl::buffer_iterator buffer_iterator; 64 | 65 | static constexpr identifier_type invalid_id = 0; 66 | 67 | field(filler_type filler, unique_impl impl); 68 | field(identifier_type id, filler_type filler, unique_impl impl); 69 | field(const field &rhs); 70 | field(field &&rhs) noexcept; 71 | 72 | field& operator=(field rhs); 73 | 74 | iterator begin(); 75 | const_iterator begin() const; 76 | iterator end(); 77 | const_iterator end() const; 78 | 79 | size_t size() const; 80 | // the number of children fields 81 | size_t field_count() const; 82 | void prepare(generation_context &context); 83 | void fill(generation_context &context); 84 | buffer_iterator fill_from_buffer(buffer_iterator start, buffer_iterator end); 85 | 86 | void accept_visitor(const visitor_type &visitor) const; 87 | 88 | void set_value(int64_t value); 89 | int64_t get_value() const; 90 | 91 | dependents_type dependent_fields() const; 92 | 93 | identifier_type id() const { 94 | return identifier; 95 | } 96 | 97 | dereference_helper operator[](size_t index); 98 | dereference_helper operator[](size_t index) const; 99 | 100 | // swap free function 101 | friend void swap(field &lhs, field &rhs); 102 | 103 | template 104 | static field from_impl(filler_type filler, Args&&... args) 105 | { 106 | return field(filler, make_unique(std::forward(args)...)); 107 | } 108 | 109 | template 110 | static field from_impl(identifier_type id, filler_type filler, Args&&... args) 111 | { 112 | return field(id, filler, make_unique(std::forward(args)...)); 113 | } 114 | 115 | static identifier_type generate_id(); 116 | private: 117 | static std::atomic global_id; 118 | 119 | 120 | unique_impl impl; 121 | filler_type filler; 122 | identifier_type identifier; 123 | }; 124 | 125 | // comparison functions 126 | bool operator<(const field &lhs, const field &rhs); 127 | 128 | template 129 | class dereference_helper { 130 | public: 131 | typedef ValueType value_type; 132 | typedef typename std::conditional< 133 | std::is_const::value, 134 | const field_impl&, 135 | field_impl& 136 | >::type wrapped_type; 137 | 138 | dereference_helper(wrapped_type impl, size_t index) 139 | : impl(impl), index(index) 140 | { 141 | 142 | } 143 | 144 | template 145 | typename std::enable_if::value, value_type>::type 146 | operator=(value_type value) 147 | { 148 | impl.set(index, value); 149 | return value; 150 | } 151 | 152 | operator value_type() const { 153 | return impl.get(index); 154 | } 155 | private: 156 | wrapped_type impl; 157 | size_t index; 158 | }; 159 | 160 | template 161 | class field_iterator : 162 | public std::iterator { 163 | public: 164 | field_iterator(field_impl &wrapper, size_t index = 0) 165 | : wrapper(wrapper), index(index) 166 | { 167 | 168 | } 169 | 170 | field_iterator& operator++() 171 | { 172 | index++; 173 | return *this; 174 | } 175 | 176 | field_iterator operator++(int) 177 | { 178 | field_iterator copied(*this); 179 | index++; 180 | return copied; 181 | } 182 | 183 | field_iterator& operator--() 184 | { 185 | index--; 186 | return *this; 187 | } 188 | 189 | dereference_helper operator*() 190 | { 191 | return dereference_helper(wrapper, index); 192 | } 193 | 194 | dereference_helper operator*() const 195 | { 196 | return dereference_helper(wrapper, index); 197 | } 198 | 199 | field_iterator operator--(int) 200 | { 201 | field_iterator copied(*this); 202 | index--; 203 | return copied; 204 | } 205 | 206 | size_t operator-(const field_iterator& rhs) 207 | { 208 | return index - rhs.index; 209 | } 210 | 211 | field_iterator operator-(size_t offset) 212 | { 213 | return field_iterator(wrapper, index - offset); 214 | } 215 | 216 | field_iterator operator+(size_t offset) 217 | { 218 | return field_iterator(wrapper, index + offset); 219 | } 220 | 221 | bool operator==(const field_iterator &rhs) const { 222 | return index == rhs.index && &wrapper.get() == &rhs.wrapper.get(); 223 | } 224 | 225 | bool operator!=(const field_iterator &rhs) const { 226 | return !(*this == rhs); 227 | } 228 | private: 229 | std::reference_wrapper wrapper; 230 | size_t index; 231 | }; 232 | 233 | 234 | #endif // FUZZER_FIELD_H 235 | -------------------------------------------------------------------------------- /include/field_filler.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #ifndef FUZZER_FIELD_FILLER_H 31 | #define FUZZER_FIELD_FILLER_H 32 | 33 | #include 34 | #include 35 | #include "functions/constraints.h" 36 | #include "field_impl.h" 37 | 38 | class field; 39 | class field_mapper; 40 | 41 | class field_filler { 42 | public: 43 | typedef field_impl::identifier_type identifier_type; 44 | typedef field_impl::dependents_type dependents_type; 45 | typedef std::unique_ptr constraint_type; 46 | 47 | // derived classes can re-implement this, it will be called 48 | // using static polymorphism 49 | static const std::array &get_constraints() { 50 | static const std::array dummy; 51 | return dummy; 52 | }; 53 | 54 | virtual ~field_filler() = default; 55 | virtual void fill(field &, generation_context &) = 0; 56 | virtual dependents_type dependent_fields() const { 57 | return { }; 58 | } 59 | }; 60 | 61 | #endif // FUZZER_FIELD_FILLER_H 62 | -------------------------------------------------------------------------------- /include/field_impl.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #ifndef FUZZER_FIELD_IMPL_H 31 | #define FUZZER_FIELD_IMPL_H 32 | 33 | #include 34 | #include 35 | #include 36 | #include "utils.h" 37 | 38 | class value_wrapper; 39 | class field; 40 | class field_mapper; 41 | class generation_context; 42 | 43 | class field_impl { 44 | public: 45 | typedef uint8_t value_type; 46 | typedef std::vector buffer_type; 47 | typedef buffer_type::const_iterator buffer_iterator; 48 | typedef std::function visitor_type; 49 | typedef unsigned int identifier_type; 50 | typedef std::vector dependents_type; 51 | 52 | virtual ~field_impl() = default; 53 | 54 | virtual std::unique_ptr clone() const = 0; 55 | virtual void prepare(generation_context &); 56 | virtual void set(size_t index, value_type value) = 0; 57 | virtual value_type get(size_t index) const = 0; 58 | virtual size_t size() const = 0; 59 | virtual size_t field_count() const; 60 | virtual void accept_visitor(const visitor_type& visitor) const { }; 61 | virtual dependents_type dependent_fields() const; 62 | virtual void set_value(int64_t value); 63 | virtual int64_t get_value() const; 64 | virtual buffer_iterator fill_from_buffer(buffer_iterator start, buffer_iterator end); 65 | private: 66 | 67 | }; 68 | 69 | // crtp so clone is always defined 70 | template 71 | class clonable_field_impl : public field_impl { 72 | public: 73 | std::unique_ptr clone() const 74 | { 75 | return make_unique(static_cast(*this)); 76 | } 77 | }; 78 | 79 | #endif // FUZZER_FIELD_IMPL_H 80 | -------------------------------------------------------------------------------- /include/field_mapper.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #ifndef FUZZER_FIELD_MAPPER_H 31 | #define FUZZER_FIELD_MAPPER_H 32 | 33 | #include 34 | #include 35 | #include 36 | #include 37 | #include 38 | #include "field.h" 39 | 40 | class field_mapper { 41 | public: 42 | field::identifier_type register_field(std::string name); 43 | void register_field(field::identifier_type id, const field &f); 44 | void identify_fields(const field &root); 45 | const field& find_field(field::identifier_type id) const; 46 | field::identifier_type find_field_name(const std::string &fname) const; 47 | field::identifier_type find_register_field_name(const std::string &fname); 48 | 49 | template 50 | void find_non_registered_fields(ForwardIterator output) 51 | { 52 | std::for_each( 53 | str2id.begin(), 54 | str2id.end(), 55 | [&](const typename decltype(str2id)::value_type& vt) { 56 | if(!vt.second.second) 57 | *output++ = vt.first; 58 | } 59 | ); 60 | } 61 | private: 62 | void visit(const field &f); 63 | 64 | std::unordered_map> str2id; 65 | std::map> id2field; 66 | }; 67 | 68 | #endif // FUZZER_FIELD_MAPPER_H 69 | -------------------------------------------------------------------------------- /include/field_serializer.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #ifndef FUZZER_FIELD_SERIALIZER_H 31 | #define FUZZER_FIELD_SERIALIZER_H 32 | 33 | #include 34 | #include 35 | #include 36 | #include 37 | #include 38 | #include 39 | #include "field.h" 40 | 41 | class field_serializer { 42 | public: 43 | typedef std::vector serialization_type; 44 | 45 | field_serializer(field root, size_t num_threads, size_t max_fields = 10); 46 | ~field_serializer(); 47 | 48 | void stop(); 49 | serialization_type next_field(); 50 | private: 51 | field_serializer(const field_serializer&) = delete; 52 | field_serializer& operator=(const field_serializer&) = delete; 53 | 54 | void thread_proc(field root); 55 | void store_field(serialization_type f); 56 | 57 | std::queue result_queue; 58 | std::vector threads; 59 | std::mutex queue_lock; 60 | std::condition_variable push_cond, pop_cond; 61 | size_t max_fields; 62 | std::atomic running; 63 | }; 64 | 65 | #endif // FUZZER_FIELD_SERIALIZER_H 66 | -------------------------------------------------------------------------------- /include/function_nodes.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #ifndef FUZZER_FUNCTION_NODES_H 31 | #define FUZZER_FUNCTION_NODES_H 32 | 33 | #include 34 | #include 35 | #include "value_node.h" 36 | #include "field_mapper.h" 37 | #include "generation_context.h" 38 | 39 | // the Functor is probably a stateless class, so surely EBCO works here 40 | template 41 | class binary_function_node : public value_node, Functor { 42 | public: 43 | typedef Functor function_type; 44 | typedef std::unique_ptr unique_node; 45 | 46 | binary_function_node(unique_node lhs, unique_node rhs, function_type function = function_type()) 47 | : Functor(std::move(function)), lhs(std::move(lhs)), rhs(std::move(rhs)) 48 | { 49 | 50 | } 51 | 52 | double eval(generation_context &ctx) 53 | { 54 | return (*this)(lhs->eval(ctx), rhs->eval(ctx)); 55 | } 56 | 57 | dependents_type dependent_fields() const 58 | { 59 | auto v1 = lhs->dependent_fields(), v2 = rhs->dependent_fields(); 60 | v1.insert(v1.end(), v2.begin(), v2.end()); 61 | return v1; 62 | } 63 | private: 64 | unique_node lhs, rhs; 65 | }; 66 | 67 | template 68 | class unary_function_node : public value_node, Functor { 69 | public: 70 | typedef Functor function_type; 71 | typedef std::unique_ptr unique_node; 72 | 73 | unary_function_node(unique_node node, function_type function = function_type()) 74 | : Functor(std::move(function)), node(std::move(node)) 75 | { 76 | 77 | } 78 | 79 | double eval(generation_context &ctx) 80 | { 81 | return (*this)(node->eval(ctx)); 82 | } 83 | 84 | dependents_type dependent_fields() const 85 | { 86 | return node->dependent_fields(); 87 | } 88 | private: 89 | unique_node node; 90 | }; 91 | 92 | class node_value_function_node : public value_node { 93 | public: 94 | node_value_function_node(field::identifier_type id) 95 | : id(id) 96 | { 97 | 98 | } 99 | 100 | double eval(generation_context &ctx) 101 | { 102 | return ctx.get_mapper().find_field(id).get_value(); 103 | } 104 | 105 | dependents_type dependent_fields() const 106 | { 107 | return { id }; 108 | } 109 | private: 110 | field::identifier_type id; 111 | }; 112 | 113 | typedef binary_function_node> plus_function_node; 114 | typedef binary_function_node> minus_function_node; 115 | typedef binary_function_node> multiplies_function_node; 116 | typedef binary_function_node> divides_function_node; 117 | typedef binary_function_node> modulus_function_node; 118 | typedef unary_function_node> negate_function_node; 119 | 120 | #endif // FUZZER_FUNCTION_NODES_H 121 | -------------------------------------------------------------------------------- /include/function_value_filler.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #ifndef FUZZER_FUNCTION_VALUE_FILLER_H 31 | #define FUZZER_FUNCTION_VALUE_FILLER_H 32 | 33 | #include 34 | #include "value_node.h" 35 | #include "field_filler.h" 36 | 37 | class function_value_filler : public field_filler { 38 | public: 39 | typedef std::unique_ptr unique_value; 40 | 41 | function_value_filler(unique_value value); 42 | 43 | void fill(field &f, generation_context &ctx); 44 | dependents_type dependent_fields() const; 45 | private: 46 | unique_value value; 47 | }; 48 | 49 | #endif // FUZZER_FUNCTION_VALUE_FILLER_H 50 | -------------------------------------------------------------------------------- /include/functions/constraints.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #ifndef FUZZER_FUNCTION_CONSTRAINT_H 31 | #define FUZZER_FUNCTION_CONSTRAINT_H 32 | 33 | #include 34 | #include 35 | 36 | namespace grammar { 37 | class field_node; 38 | } 39 | 40 | class field_impl; 41 | 42 | class function_constraint { 43 | public: 44 | virtual ~function_constraint() = default; 45 | 46 | virtual void check(const grammar::field_node &f) const = 0; 47 | virtual std::unique_ptr field_impl_from_constraint() const; 48 | }; 49 | 50 | class required_size_constraint : public function_constraint { 51 | public: 52 | required_size_constraint(size_t required); 53 | void check(const grammar::field_node &f) const; 54 | std::unique_ptr field_impl_from_constraint() const; 55 | private: 56 | size_t required; 57 | }; 58 | 59 | #endif // FUZZER_FUNCTION_CONSTRAINT_H 60 | -------------------------------------------------------------------------------- /include/functions/crc.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #ifndef FUZZER_CRC_H 31 | #define FUZZER_CRC_H 32 | 33 | #include "unary_field_function.h" 34 | 35 | class crc32_function : public unary_field_function { 36 | public: 37 | crc32_function(identifier_type id); 38 | 39 | double apply(const field &input_field); 40 | }; 41 | 42 | #endif // FUZZER_CRC_H 43 | -------------------------------------------------------------------------------- /include/functions/hashing.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #ifndef FUZZER_FUNCTION_HASHING_H 31 | #define FUZZER_FUNCTION_HASHING_H 32 | 33 | #include 34 | #include "constraints.h" 35 | #include "unary_field_function.h" 36 | 37 | class md5_function : public unary_field_filler_function { 38 | public: 39 | md5_function(identifier_type id); 40 | 41 | void apply(const field &input_field, field &output_field); 42 | 43 | static const std::array &get_constraints(); 44 | }; 45 | 46 | class sha1_function : public unary_field_filler_function { 47 | public: 48 | sha1_function(identifier_type id); 49 | 50 | void apply(const field &input_field, field &output_field); 51 | 52 | static const std::array &get_constraints(); 53 | }; 54 | 55 | #endif // FUZZER_FUNCTION_HASHING_H 56 | -------------------------------------------------------------------------------- /include/functions/misc.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #ifndef FUZZER_FUNCTION_SIZE_H 31 | #define FUZZER_FUNCTION_SIZE_H 32 | 33 | #include "unary_field_function.h" 34 | 35 | template 36 | class generic_field_function : public unary_field_function> { 37 | public: 38 | typedef typename unary_field_function>::identifier_type identifier_type; 39 | 40 | 41 | generic_field_function(identifier_type id) 42 | : unary_field_function>(id) 43 | { 44 | 45 | } 46 | 47 | double apply(const field &input_field) 48 | { 49 | return (input_field.*MemFun)(); 50 | } 51 | }; 52 | 53 | typedef generic_field_function<&field::size> size_function; 54 | typedef generic_field_function<&field::field_count> field_count_function; 55 | 56 | #endif // FUZZER_FUNCTION_SIZE_H 57 | -------------------------------------------------------------------------------- /include/functions/random.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #ifndef FUZZER_FUNCTION_RANDOM_H 31 | #define FUZZER_FUNCTION_RANDOM_H 32 | 33 | #include "field_filler.h" 34 | 35 | class random_function : public field_filler { 36 | public: 37 | void fill(field &f, generation_context &ctx); 38 | }; 39 | 40 | class bitrandom_function : public field_filler { 41 | public: 42 | void fill(field &f, generation_context &ctx); 43 | }; 44 | 45 | #endif // FUZZER_FUNCTION_RANDOM_H 46 | -------------------------------------------------------------------------------- /include/generation_context.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #ifndef FUZZER_GENERATION_CONTEXT_H 31 | #define FUZZER_GENERATION_CONTEXT_H 32 | 33 | #include 34 | #include "field_mapper.h" 35 | 36 | class generation_context { 37 | public: 38 | typedef std::mt19937 random_generator; 39 | 40 | generation_context(random_generator::result_type seed); 41 | 42 | field_mapper &get_mapper(); 43 | const field_mapper &get_mapper() const; 44 | random_generator &get_random_generator(); 45 | private: 46 | field_mapper mapper; 47 | random_generator rnd; 48 | }; 49 | 50 | #endif // FUZZER_GENERATION_CONTEXT_H 51 | -------------------------------------------------------------------------------- /include/multiptr_destructor.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #ifndef FUZZER_MULTIPTR_DESTRUCTOR_H 31 | #define FUZZER_MULTIPTR_DESTRUCTOR_H 32 | 33 | #include 34 | #include 35 | #include 36 | #include 37 | 38 | template 39 | class multiptr_destructor { 40 | public: 41 | template 42 | void store_pointer(T *ptr) { 43 | internal_store<0>(ptr); 44 | } 45 | private: 46 | template 47 | using ptr_vector = std::vector>; 48 | 49 | template 50 | using tup_elem = typename std::tuple_element>::type; 51 | 52 | template 53 | using enabler = std::enable_if, T>::value, void>; 54 | 55 | template 56 | using disabler = std::enable_if, T>::value, void>; 57 | 58 | template 59 | typename disabler::type internal_store(T* ptr) { 60 | internal_store(ptr); 61 | } 62 | 63 | template 64 | typename enabler::type internal_store(T* ptr) { 65 | std::get(vector_tuple).push_back(std::unique_ptr(ptr)); 66 | } 67 | 68 | 69 | std::tuple...> vector_tuple; 70 | }; 71 | 72 | #endif // FUZZER_MULTIPTR_DESTRUCTOR_H 73 | -------------------------------------------------------------------------------- /include/parser/syntax.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #ifndef FUZZER_SYNTAX_H 31 | #define FUZZER_SYNTAX_H 32 | 33 | #include 34 | #include 35 | 36 | #ifndef YYLTYPE_IS_DECLARED 37 | #define YYLTYPE_IS_DECLARED 38 | 39 | struct YYLTYPE 40 | { 41 | int first_line; 42 | int first_column; 43 | int last_line; 44 | int last_column; 45 | }; 46 | 47 | #endif 48 | 49 | #ifndef YYTOKENTYPE 50 | # define YYTOKENTYPE 51 | 52 | enum fuzzer_identifiers { 53 | TEMPLATE = 258, 54 | IDENTIFIER, 55 | INT_CONST, 56 | TEMPLATES, 57 | BLOCK, 58 | COMPOUND_BLOCK, 59 | VAR_BLOCK, 60 | STR_CONST, 61 | ERROR, 62 | COMPOUND_BITFIELD, 63 | BITFIELD, 64 | STR_BLOCK, 65 | CHOICE_FIELD, 66 | AUTO_FIELD 67 | }; 68 | #endif 69 | 70 | #endif // FUZZER_SYNTAX_H 71 | -------------------------------------------------------------------------------- /include/parser/syntax.tab.h: -------------------------------------------------------------------------------- 1 | /* A Bison parser, made by GNU Bison 2.5. */ 2 | 3 | /* Bison interface for Yacc-like parsers in C 4 | 5 | Copyright (C) 1984, 1989-1990, 2000-2011 Free Software Foundation, Inc. 6 | 7 | This program is free software: you can redistribute it and/or modify 8 | it under the terms of the GNU General Public License as published by 9 | the Free Software Foundation, either version 3 of the License, or 10 | (at your option) any later version. 11 | 12 | This program is distributed in the hope that it will be useful, 13 | but WITHOUT ANY WARRANTY; without even the implied warranty of 14 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 15 | GNU General Public License for more details. 16 | 17 | You should have received a copy of the GNU General Public License 18 | along with this program. If not, see . */ 19 | 20 | /* As a special exception, you may create a larger work that contains 21 | part or all of the Bison parser skeleton and distribute that work 22 | under terms of your choice, so long as that work isn't itself a 23 | parser generator using the skeleton or a modified version thereof 24 | as a parser skeleton. Alternatively, if you modify or redistribute 25 | the parser skeleton itself, you may (at your option) remove this 26 | special exception, which will cause the skeleton and the resulting 27 | Bison output files to be licensed under the GNU General Public 28 | License without this special exception. 29 | 30 | This special exception was added by the Free Software Foundation in 31 | version 2.2 of Bison. */ 32 | 33 | 34 | /* Tokens. */ 35 | #ifndef YYTOKENTYPE 36 | # define YYTOKENTYPE 37 | /* Put the tokens into the symbol table, so that GDB and other debuggers 38 | know about them. */ 39 | enum yytokentype { 40 | TEMPLATE = 258, 41 | BLOCK = 262, 42 | TEMPLATES = 261, 43 | COMPOUND_BLOCK = 263, 44 | VAR_BLOCK = 264, 45 | COMPOUND_BITFIELD = 267, 46 | BITFIELD = 268, 47 | STR_BLOCK = 269, 48 | CHOICE_FIELD = 270, 49 | AUTO_FIELD = 271, 50 | IDENTIFIER = 259, 51 | STR_CONST = 265, 52 | INT_CONST = 260 53 | }; 54 | #endif 55 | /* Tokens. */ 56 | #define TEMPLATE 258 57 | #define BLOCK 262 58 | #define TEMPLATES 261 59 | #define COMPOUND_BLOCK 263 60 | #define VAR_BLOCK 264 61 | #define COMPOUND_BITFIELD 267 62 | #define BITFIELD 268 63 | #define STR_BLOCK 269 64 | #define CHOICE_FIELD 270 65 | #define AUTO_FIELD 271 66 | #define IDENTIFIER 259 67 | #define STR_CONST 265 68 | #define INT_CONST 260 69 | 70 | 71 | 72 | 73 | #if ! defined YYSTYPE && ! defined YYSTYPE_IS_DECLARED 74 | typedef union YYSTYPE 75 | { 76 | 77 | /* Line 2068 of yacc.c */ 78 | #line 40 "parser/grammar.y" 79 | 80 | grammar::field_node* ast_field; 81 | grammar::filler_node* ast_filler; 82 | grammar::value_node* ast_value_node; 83 | grammar::script* ast_script; 84 | grammar::template_def_node* ast_template_def; 85 | std::vector *ast_fields; 86 | uint64_t int_val; 87 | std::string *symbol; 88 | const char *error_msg; 89 | 90 | 91 | 92 | /* Line 2068 of yacc.c */ 93 | #line 94 "parser/grammar-output.h" 94 | } YYSTYPE; 95 | # define YYSTYPE_IS_TRIVIAL 1 96 | # define yystype YYSTYPE /* obsolescent; will be withdrawn */ 97 | # define YYSTYPE_IS_DECLARED 1 98 | #endif 99 | 100 | extern YYSTYPE yylval; 101 | 102 | #if ! defined YYLTYPE && ! defined YYLTYPE_IS_DECLARED 103 | typedef struct YYLTYPE 104 | { 105 | int first_line; 106 | int first_column; 107 | int last_line; 108 | int last_column; 109 | } YYLTYPE; 110 | # define yyltype YYLTYPE /* obsolescent; will be withdrawn */ 111 | # define YYLTYPE_IS_DECLARED 1 112 | # define YYLTYPE_IS_TRIVIAL 1 113 | #endif 114 | 115 | extern YYLTYPE yylloc; 116 | 117 | -------------------------------------------------------------------------------- /include/parser/syntax_parser.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #ifndef FUZZER_SYNTAX_PARSER_H 31 | #define FUZZER_SYNTAX_PARSER_H 32 | 33 | #include 34 | #include 35 | #include 36 | #include 37 | #include 38 | #include "parser/nodes.h" 39 | #include "field_mapper.h" 40 | #include "field_filler.h" 41 | #include "utils.h" 42 | #include "multiptr_destructor.h" 43 | 44 | class field; 45 | 46 | class syntax_parser { 47 | public: 48 | typedef std::shared_ptr filler_ptr; 49 | typedef std::function filler_fun_type; 50 | typedef std::function value_fun_type; 51 | typedef field_filler::identifier_type identifier_type; 52 | typedef grammar::value_node value_node; 53 | typedef grammar::field_node field_node; 54 | typedef grammar::filler_node filler_node; 55 | typedef grammar::fields_list fields_list; 56 | typedef grammar::template_def_node template_def_node; 57 | 58 | syntax_parser(); 59 | 60 | void parse(const std::string &file_name); 61 | void parse(std::istream &input); 62 | void add_template(std::string name, grammar::template_def_node *node); 63 | field allocate_template(const std::string &name, size_t min, size_t max); 64 | 65 | 66 | void set_script(grammar::script* scr); 67 | field get_root_field(); 68 | field_mapper &get_mapper(); 69 | 70 | template 71 | void register_filler_function(std::string name, Functor &&ptr) 72 | { 73 | filler_functions.insert(std::make_pair(std::move(name), std::move(ptr))); 74 | } 75 | 76 | template 77 | void register_value_function(std::string name, Functor &&ptr) 78 | { 79 | value_functions.insert(std::make_pair(std::move(name), std::move(ptr))); 80 | } 81 | 82 | bool is_filler_function(const std::string &name); 83 | bool is_value_function(const std::string &name); 84 | 85 | /* ************** Allocator functions ******************/ 86 | 87 | // block field 88 | 89 | field_node *make_block_node(filler_node *filler, size_t size); 90 | field_node *make_block_node(filler_node *filler, size_t size, const std::string &name); 91 | 92 | // auto field 93 | 94 | field_node *make_auto_node(filler_node *filler); 95 | field_node *make_auto_node(filler_node *filler, const std::string &name); 96 | 97 | // bit field 98 | 99 | field_node *make_bitfield_node(value_node *vnode, size_t size); 100 | field_node *make_bitfield_node(value_node *vnode, size_t size, const std::string &name); 101 | 102 | // variable block 103 | 104 | field_node *make_variable_block_node(filler_node *filler, size_t min_size, size_t max_size); 105 | field_node *make_variable_block_node(filler_node *filler, size_t min_size, size_t max_size, 106 | const std::string &name); 107 | 108 | // compound 109 | 110 | field_node *make_compound_field_node(fields_list *fields); 111 | field_node *make_compound_field_node(fields_list *fields, const std::string &name); 112 | 113 | // compound bitfield 114 | 115 | field_node *make_compound_bitfield_node(fields_list *fields); 116 | field_node *make_compound_bitfield_node(fields_list *fields, const std::string &name); 117 | 118 | // choice field 119 | 120 | field_node *make_choice_field_node(fields_list *fields); 121 | field_node *make_choice_field_node(fields_list *fields, const std::string &name); 122 | 123 | // template field 124 | 125 | field_node *make_template_field_node(const std::string &template_name, 126 | size_t min, size_t max); 127 | 128 | // template def field 129 | 130 | template_def_node *make_template_def_node(fields_list *fields); 131 | 132 | // fields list 133 | 134 | fields_list *make_fields_list(); 135 | 136 | // stuff 137 | 138 | value_node *make_const_value_node(double f); 139 | filler_node *make_const_string_node(const std::string &str); 140 | value_node *make_node_value_node(const std::string &name); 141 | filler_node *make_node_filler_node(const std::string &field_name, 142 | const std::string &function_name); 143 | value_node *make_node_value_function_node(const std::string &field_name, 144 | const std::string &function_name); 145 | filler_node *make_function_value_filler_node(value_node *node); 146 | 147 | // 148 | 149 | template 150 | std::string *make_string(Ts&&... args) 151 | { 152 | return node_alloc(std::forward(args)...); 153 | } 154 | 155 | grammar::script *make_script(); 156 | 157 | template 158 | value_node *make_binary_function_value_node(value_node *lhs, value_node *rhs) 159 | { 160 | return node_alloc>(lhs, rhs); 161 | } 162 | private: 163 | template 164 | struct line_number_setter { 165 | template 166 | static void set(size_t, T*) { } 167 | }; 168 | 169 | template 170 | T *node_alloc(Args&&... args) 171 | { 172 | extern int curr_lineno; 173 | 174 | auto smart_ptr = make_unique(std::forward(args)...); 175 | auto ptr = smart_ptr.get(); 176 | line_number_setter::value>::set(curr_lineno, ptr); 177 | destructor.store_pointer(smart_ptr.release()); 178 | return ptr; 179 | } 180 | 181 | template 182 | void register_filler_function(const std::string &name) 183 | { 184 | register_filler_function( 185 | name, 186 | [&](identifier_type id) { 187 | return node_alloc>(id); 188 | } 189 | ); 190 | } 191 | 192 | template 193 | void register_value_function(const std::string &name) 194 | { 195 | register_value_function( 196 | name, 197 | [&](identifier_type id) { 198 | return node_alloc>(id); 199 | } 200 | ); 201 | } 202 | 203 | filler_node* allocate_filler_function(const std::string &name, identifier_type id); 204 | value_node* allocate_value_function(const std::string &name, identifier_type id); 205 | grammar::script* script_root; 206 | field_mapper mapper; 207 | std::map filler_functions; 208 | std::map value_functions; 209 | std::map templates; 210 | multiptr_destructor< 211 | field_node, 212 | filler_node, 213 | fields_list, 214 | template_def_node, 215 | value_node, 216 | std::string, 217 | grammar::script 218 | > destructor; 219 | }; 220 | 221 | template<> 222 | struct syntax_parser::line_number_setter { 223 | template 224 | static void set(size_t line, T *ptr) { 225 | ptr->set_line_number(line); 226 | } 227 | }; 228 | 229 | #endif // FUZZER_SYNTAX_PARSER_H 230 | -------------------------------------------------------------------------------- /include/template_field.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #ifndef FUZZER_TEMPLATE_BLOCK_H 31 | #define FUZZER_TEMPLATE_BLOCK_H 32 | 33 | #include 34 | #include "compound_field.h" 35 | 36 | class template_field_impl : public compound_field_impl { 37 | public: 38 | template_field_impl(field tmp_field, size_t min, size_t max); 39 | 40 | std::unique_ptr clone() const; 41 | void prepare(generation_context &); 42 | dependents_type dependent_fields() const; 43 | private: 44 | field template_field; 45 | std::vector ordered, unresolved; 46 | std::vector generated_fields; 47 | std::uniform_int_distribution distr; 48 | }; 49 | 50 | #endif // FUZZER_TEMPLATE_BLOCK_H 51 | -------------------------------------------------------------------------------- /include/topological_sorter.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #ifndef FUZZER_TOPOLOGICAL_SORTER_H 31 | #define FUZZER_TOPOLOGICAL_SORTER_H 32 | 33 | #include 34 | #include 35 | #include "field_impl.h" 36 | 37 | class field; 38 | 39 | class topological_sorter { 40 | public: 41 | typedef std::vector fields_type; 42 | 43 | fields_type topological_sort(const field &f); 44 | fields_type topological_sort(const field &f, std::set &unresolved); 45 | private: 46 | 47 | }; 48 | 49 | #endif // FUZZER_TOPOLOGICAL_SORTER_H 50 | -------------------------------------------------------------------------------- /include/unary_field_function.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #ifndef FUZZER_UNARY_FIELD_FUNCTION_H 31 | #define FUZZER_UNARY_FIELD_FUNCTION_H 32 | 33 | #include "field.h" 34 | #include "value_node.h" 35 | #include "generation_context.h" 36 | 37 | template 38 | class unary_field_function : public value_node { 39 | public: 40 | unary_field_function(identifier_type id) 41 | : id(id) 42 | { 43 | 44 | } 45 | 46 | double eval(generation_context &ctx) 47 | { 48 | return static_cast(*this).apply(ctx.get_mapper().find_field(id)); 49 | } 50 | 51 | dependents_type dependent_fields() const 52 | { 53 | return { id }; 54 | } 55 | private: 56 | // The dispatched method should follow this signature: 57 | //double apply(const field &input_field); 58 | 59 | identifier_type id; 60 | }; 61 | 62 | template 63 | class unary_field_filler_function : public field_filler { 64 | public: 65 | unary_field_filler_function(identifier_type id) 66 | : id(id) 67 | { 68 | 69 | } 70 | void fill(field &f, generation_context &ctx) 71 | { 72 | static_cast(*this).apply(ctx.get_mapper().find_field(id), f); 73 | } 74 | 75 | dependents_type dependent_fields() const 76 | { 77 | return { id }; 78 | } 79 | private: 80 | // The dispatched method should follow this signature: 81 | // void apply(const field &input_field, field &output_field); 82 | 83 | identifier_type id; 84 | }; 85 | 86 | #endif // FUZZER_UNARY_FIELD_FUNCTION_H 87 | -------------------------------------------------------------------------------- /include/utils.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #ifndef FUZZER_UTILS_H 31 | #define FUZZER_UTILS_H 32 | 33 | #include 34 | 35 | template 36 | std::unique_ptr make_unique(Args&&... args) 37 | { 38 | return std::unique_ptr(new T(std::forward(args)...)); 39 | } 40 | 41 | #endif // FUZZER_UTILS_H 42 | -------------------------------------------------------------------------------- /include/value_filler.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #ifndef FUZZER_VALUE_FILLER_H 31 | #define FUZZER_VALUE_FILLER_H 32 | 33 | #include 34 | #include 35 | #include "field_filler.h" 36 | #include "field.h" 37 | 38 | class value_filler : public field_filler { 39 | public: 40 | template 41 | value_filler(ForwardIterator start, ForwardIterator end) 42 | : data(start, end) 43 | { 44 | 45 | } 46 | 47 | value_filler(const std::string &str); 48 | 49 | void fill(field &f, const field_mapper&); 50 | private: 51 | std::vector data; 52 | }; 53 | 54 | #endif // FUZZER_VALUE_FILLER_H 55 | -------------------------------------------------------------------------------- /include/value_node.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #ifndef FUZZER_VALUE_NODE_H 31 | #define FUZZER_VALUE_NODE_H 32 | 33 | #include "field_impl.h" 34 | 35 | class field_mapper; 36 | class generation_context; 37 | 38 | class value_node { 39 | public: 40 | typedef field_impl::identifier_type identifier_type; 41 | typedef field_impl::dependents_type dependents_type; 42 | 43 | virtual ~value_node() noexcept = default; 44 | virtual double eval(generation_context &) = 0; 45 | virtual dependents_type dependent_fields() const { 46 | return { }; 47 | } 48 | }; 49 | 50 | #endif // FUZZER_VALUE_NODE_H 51 | -------------------------------------------------------------------------------- /include/variable_block_field.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #ifndef FUZZER_VARIABLE_BLOCK_FIELD_H 31 | #define FUZZER_VARIABLE_BLOCK_FIELD_H 32 | 33 | #include 34 | #include 35 | #include "field_impl.h" 36 | 37 | class variable_block_field_impl : public clonable_field_impl { 38 | public: 39 | typedef std::vector container_type; 40 | 41 | variable_block_field_impl(size_t min_size, size_t max_size); 42 | 43 | void set(size_t index, value_type value); 44 | value_type get(size_t index) const; 45 | size_t size() const; 46 | void prepare(generation_context &context); 47 | buffer_iterator fill_from_buffer(buffer_iterator start, buffer_iterator end); 48 | private: 49 | container_type data; 50 | std::uniform_int_distribution distribution; 51 | }; 52 | 53 | #endif // FUZZER_VARIABLE_BLOCK_FIELD_H 54 | -------------------------------------------------------------------------------- /m4/ax_cxx_compile_stdcxx_11.m4: -------------------------------------------------------------------------------- 1 | # ============================================================================ 2 | # http://www.gnu.org/software/autoconf-archive/ax_cxx_compile_stdcxx_11.html 3 | # ============================================================================ 4 | # 5 | # SYNOPSIS 6 | # 7 | # AX_CXX_COMPILE_STDCXX_11([ext|noext],[mandatory|optional]) 8 | # 9 | # DESCRIPTION 10 | # 11 | # Check for baseline language coverage in the compiler for the C++11 12 | # standard; if necessary, add switches to CXXFLAGS to enable support. 13 | # 14 | # The first argument, if specified, indicates whether you insist on an 15 | # extended mode (e.g. -std=gnu++11) or a strict conformance mode (e.g. 16 | # -std=c++11). If neither is specified, you get whatever works, with 17 | # preference for an extended mode. 18 | # 19 | # The second argument, if specified 'mandatory' or if left unspecified, 20 | # indicates that baseline C++11 support is required and that the macro 21 | # should error out if no mode with that support is found. If specified 22 | # 'optional', then configuration proceeds regardless, after defining 23 | # HAVE_CXX11 if and only if a supporting mode is found. 24 | # 25 | # LICENSE 26 | # 27 | # Copyright (c) 2008 Benjamin Kosnik 28 | # Copyright (c) 2012 Zack Weinberg 29 | # Copyright (c) 2013 Roy Stogner 30 | # 31 | # Copying and distribution of this file, with or without modification, are 32 | # permitted in any medium without royalty provided the copyright notice 33 | # and this notice are preserved. This file is offered as-is, without any 34 | # warranty. 35 | 36 | #serial 3 37 | 38 | m4_define([_AX_CXX_COMPILE_STDCXX_11_testbody], [ 39 | template 40 | struct check 41 | { 42 | static_assert(sizeof(int) <= sizeof(T), "not big enough"); 43 | }; 44 | 45 | typedef check> right_angle_brackets; 46 | 47 | int a; 48 | decltype(a) b; 49 | 50 | typedef check check_type; 51 | check_type c; 52 | check_type&& cr = static_cast(c); 53 | 54 | auto d = a; 55 | ]) 56 | 57 | AC_DEFUN([AX_CXX_COMPILE_STDCXX_11], [dnl 58 | m4_if([$1], [], [], 59 | [$1], [ext], [], 60 | [$1], [noext], [], 61 | [m4_fatal([invalid argument `$1' to AX_CXX_COMPILE_STDCXX_11])])dnl 62 | m4_if([$2], [], [ax_cxx_compile_cxx11_required=true], 63 | [$2], [mandatory], [ax_cxx_compile_cxx11_required=true], 64 | [$2], [optional], [ax_cxx_compile_cxx11_required=false], 65 | [m4_fatal([invalid second argument `$2' to AX_CXX_COMPILE_STDCXX_11])])dnl 66 | AC_LANG_PUSH([C++])dnl 67 | ac_success=no 68 | AC_CACHE_CHECK(whether $CXX supports C++11 features by default, 69 | ax_cv_cxx_compile_cxx11, 70 | [AC_COMPILE_IFELSE([AC_LANG_SOURCE([_AX_CXX_COMPILE_STDCXX_11_testbody])], 71 | [ax_cv_cxx_compile_cxx11=yes], 72 | [ax_cv_cxx_compile_cxx11=no])]) 73 | if test x$ax_cv_cxx_compile_cxx11 = xyes; then 74 | ac_success=yes 75 | fi 76 | 77 | m4_if([$1], [noext], [], [dnl 78 | if test x$ac_success = xno; then 79 | for switch in -std=gnu++11 -std=gnu++0x; do 80 | cachevar=AS_TR_SH([ax_cv_cxx_compile_cxx11_$switch]) 81 | AC_CACHE_CHECK(whether $CXX supports C++11 features with $switch, 82 | $cachevar, 83 | [ac_save_CXXFLAGS="$CXXFLAGS" 84 | CXXFLAGS="$CXXFLAGS $switch" 85 | AC_COMPILE_IFELSE([AC_LANG_SOURCE([_AX_CXX_COMPILE_STDCXX_11_testbody])], 86 | [eval $cachevar=yes], 87 | [eval $cachevar=no]) 88 | CXXFLAGS="$ac_save_CXXFLAGS"]) 89 | if eval test x\$$cachevar = xyes; then 90 | CXXFLAGS="$CXXFLAGS $switch" 91 | ac_success=yes 92 | break 93 | fi 94 | done 95 | fi]) 96 | 97 | m4_if([$1], [ext], [], [dnl 98 | if test x$ac_success = xno; then 99 | for switch in -std=c++11 -std=c++0x; do 100 | cachevar=AS_TR_SH([ax_cv_cxx_compile_cxx11_$switch]) 101 | AC_CACHE_CHECK(whether $CXX supports C++11 features with $switch, 102 | $cachevar, 103 | [ac_save_CXXFLAGS="$CXXFLAGS" 104 | CXXFLAGS="$CXXFLAGS $switch" 105 | AC_COMPILE_IFELSE([AC_LANG_SOURCE([_AX_CXX_COMPILE_STDCXX_11_testbody])], 106 | [eval $cachevar=yes], 107 | [eval $cachevar=no]) 108 | CXXFLAGS="$ac_save_CXXFLAGS"]) 109 | if eval test x\$$cachevar = xyes; then 110 | CXXFLAGS="$CXXFLAGS $switch" 111 | ac_success=yes 112 | break 113 | fi 114 | done 115 | fi]) 116 | AC_LANG_POP([C++]) 117 | if test x$ax_cxx_compile_cxx11_required = xtrue; then 118 | if test x$ac_success = xno; then 119 | AC_MSG_ERROR([*** A compiler with support for C++11 language features is required.]) 120 | fi 121 | else 122 | if test x$ac_success = xno; then 123 | HAVE_CXX11=0 124 | AC_MSG_NOTICE([No compiler with C++11 support was found]) 125 | else 126 | HAVE_CXX11=1 127 | AC_DEFINE(HAVE_CXX11,1, 128 | [define if the compiler supports basic C++11 syntax]) 129 | fi 130 | 131 | AC_SUBST(HAVE_CXX11) 132 | fi 133 | ]) 134 | 135 | -------------------------------------------------------------------------------- /parser/grammar.y: -------------------------------------------------------------------------------- 1 | %{ 2 | 3 | #include 4 | #include 5 | #include 6 | #include 7 | #include "parser/nodes.h" 8 | #include "parser/syntax.h" 9 | #include "parser/syntax_parser.h" 10 | #include "function_nodes.h" 11 | 12 | extern int curr_lineno; 13 | int num_errors = 0; 14 | 15 | extern syntax_parser* grammar_syntax_parser; 16 | 17 | void yyerror(const char *s) 18 | { 19 | extern int curr_lineno; 20 | 21 | std::cerr << "error in line " << curr_lineno << ": " 22 | << s << std::endl; 23 | } 24 | 25 | extern "C" 26 | { 27 | int yyparse(); 28 | int yylex(); 29 | int yywrap() 30 | { 31 | return 1; 32 | } 33 | } 34 | 35 | %} 36 | 37 | %locations 38 | %error-verbose 39 | 40 | %union { 41 | grammar::field_node* ast_field; 42 | grammar::filler_node* ast_filler; 43 | grammar::value_node* ast_value_node; 44 | grammar::script* ast_script; 45 | grammar::template_def_node* ast_template_def; 46 | std::vector *ast_fields; 47 | uint64_t int_val; 48 | std::string *symbol; 49 | const char *error_msg; 50 | } 51 | 52 | %token TEMPLATE 258 BLOCK 262 TEMPLATES 261 COMPOUND_BLOCK 263 VAR_BLOCK 264 53 | %token COMPOUND_BITFIELD 267 BITFIELD 268 STR_BLOCK 269 CHOICE_FIELD 270 54 | %token AUTO_FIELD 271 55 | %token '<' '>' ';' '+' '-' '/' '*' '{' '}' '(' ')' ',' 56 | %token IDENTIFIER 259 STR_CONST 265 57 | %token INT_CONST 260 58 | 59 | %type field block_field compound_field var_block template_field 60 | %type choice_field compound_bitfield bitfield auto_field 61 | %type template_def 62 | %type script 63 | %type fields templates bitfields 64 | %type expression expression_func 65 | %type filler filler_function 66 | 67 | %left '-' '+' 68 | %left '*' '/' 69 | 70 | %start script 71 | 72 | 73 | %% 74 | 75 | script: 76 | TEMPLATES '{' templates '}' ';' fields { 77 | if(num_errors == 0) { 78 | auto s = grammar_syntax_parser->make_script(); 79 | for(auto &i : *$6) 80 | s->add_field_node(std::move(i)); 81 | grammar_syntax_parser->set_script(s); 82 | } 83 | } 84 | | 85 | fields { 86 | if(num_errors == 0) { 87 | auto s = grammar_syntax_parser->make_script(); 88 | for(auto &i : *$1) 89 | s->add_field_node(std::move(i)); 90 | grammar_syntax_parser->set_script(s); 91 | } 92 | } 93 | ; 94 | 95 | templates: 96 | templates template_def { 97 | $$ = nullptr; 98 | } 99 | | 100 | template_def { 101 | $$ = nullptr; 102 | } 103 | ; 104 | 105 | template_def: 106 | IDENTIFIER '{' fields '}' ';' { 107 | $$ = grammar_syntax_parser->make_template_def_node($3); 108 | grammar_syntax_parser->add_template(*$1, $$); 109 | } 110 | ; 111 | 112 | fields: 113 | field { 114 | $$ = grammar_syntax_parser->make_fields_list(); 115 | if($1) 116 | $$->push_back($1); 117 | } 118 | | 119 | fields field { 120 | if($2) 121 | $1->push_back($2); 122 | } 123 | ; 124 | 125 | field: 126 | block_field { $$ = $1; } 127 | | 128 | compound_field { $$ = $1; } 129 | | 130 | var_block { $$ = $1; } 131 | | 132 | template_field { $$ = $1; } 133 | | 134 | compound_bitfield { $$ = $1; } 135 | | 136 | choice_field { $$ = $1; } 137 | | 138 | auto_field { $$ = $1; } 139 | | 140 | error ';' { num_errors++; yyerrok; } 141 | ; 142 | 143 | block_field: 144 | BLOCK '<' INT_CONST '>' IDENTIFIER '=' filler ';' { 145 | $$ = grammar_syntax_parser->make_block_node($7, $3, *$5); 146 | } 147 | | 148 | BLOCK '<' INT_CONST '>' IDENTIFIER ';' { 149 | $$ = grammar_syntax_parser->make_block_node(nullptr, $3, *$5); 150 | } 151 | | 152 | BLOCK '<' INT_CONST '>' '=' filler ';' { 153 | $$ = grammar_syntax_parser->make_block_node($6, $3); 154 | } 155 | | 156 | BLOCK '<' INT_CONST '>' ';' { 157 | $$ = grammar_syntax_parser->make_block_node(nullptr, $3); 158 | } 159 | | 160 | STR_BLOCK '=' STR_CONST ';' { 161 | $$ = grammar_syntax_parser->make_block_node( 162 | grammar_syntax_parser->make_const_string_node(*$3), 163 | $3->size() 164 | ); 165 | } 166 | | 167 | STR_BLOCK IDENTIFIER '=' STR_CONST ';' { 168 | $$ = grammar_syntax_parser->make_block_node( 169 | grammar_syntax_parser->make_const_string_node(*$4), 170 | $4->size(), 171 | *$2 172 | ); 173 | } 174 | ; 175 | 176 | auto_field: 177 | AUTO_FIELD IDENTIFIER '=' filler ';' { 178 | $$ = grammar_syntax_parser->make_auto_node($4, *$2); 179 | } 180 | | 181 | AUTO_FIELD '=' filler ';' { 182 | $$ = grammar_syntax_parser->make_auto_node($3); 183 | } 184 | ; 185 | 186 | var_block: 187 | VAR_BLOCK '<' INT_CONST ',' INT_CONST '>' IDENTIFIER '=' filler ';' { 188 | $$ = grammar_syntax_parser->make_variable_block_node($9, $3, $5, *$7); 189 | } 190 | | 191 | VAR_BLOCK '<' INT_CONST ',' INT_CONST '>' IDENTIFIER ';' { 192 | $$ = grammar_syntax_parser->make_variable_block_node(nullptr, $3, $5, *$7); 193 | } 194 | | 195 | VAR_BLOCK '<' INT_CONST ',' INT_CONST '>' '=' filler ';' { 196 | $$ = grammar_syntax_parser->make_variable_block_node($8, $3, $5); 197 | } 198 | | 199 | VAR_BLOCK '<' INT_CONST ',' INT_CONST '>' ';' { 200 | $$ = grammar_syntax_parser->make_variable_block_node(nullptr, $3, $5); 201 | } 202 | ; 203 | 204 | compound_field: 205 | COMPOUND_BLOCK '{' fields '}' ';' { 206 | $$ = grammar_syntax_parser->make_compound_field_node($3); 207 | } 208 | | 209 | COMPOUND_BLOCK IDENTIFIER '{' fields '}' ';' { 210 | $$ = grammar_syntax_parser->make_compound_field_node($4, *$2); 211 | } 212 | ; 213 | 214 | compound_bitfield: 215 | COMPOUND_BITFIELD '{' bitfields '}' ';' { 216 | $$ = grammar_syntax_parser->make_compound_bitfield_node($3); 217 | } 218 | | 219 | COMPOUND_BITFIELD IDENTIFIER '{' bitfields '}' ';' { 220 | $$ = grammar_syntax_parser->make_compound_bitfield_node($4, *$2); 221 | } 222 | ; 223 | 224 | choice_field: 225 | CHOICE_FIELD '{' fields '}' ';' { 226 | $$ = grammar_syntax_parser->make_choice_field_node($3); 227 | } 228 | | 229 | CHOICE_FIELD IDENTIFIER '{' fields '}' ';' { 230 | $$ = grammar_syntax_parser->make_choice_field_node($4, *$2); 231 | } 232 | ; 233 | 234 | 235 | bitfields: 236 | bitfield { 237 | $$ = grammar_syntax_parser->make_fields_list(); 238 | $$->push_back($1); 239 | } 240 | | 241 | bitfields bitfield { 242 | $1->push_back($2); 243 | } 244 | ; 245 | 246 | bitfield: 247 | BITFIELD '<' INT_CONST '>' IDENTIFIER '=' expression ';' { 248 | $$ = grammar_syntax_parser->make_bitfield_node($7, $3, *$5); 249 | } 250 | | 251 | BITFIELD '<' INT_CONST '>' IDENTIFIER ';' { 252 | $$ = grammar_syntax_parser->make_bitfield_node(nullptr, $3, *$5); 253 | } 254 | | 255 | BITFIELD '<' INT_CONST '>' '=' expression ';' { 256 | $$ = grammar_syntax_parser->make_bitfield_node($6, $3); 257 | } 258 | | 259 | BITFIELD '<' INT_CONST '>' ';' { 260 | $$ = grammar_syntax_parser->make_bitfield_node(nullptr, $3); 261 | } 262 | ; 263 | 264 | template_field: 265 | TEMPLATE '<' IDENTIFIER ',' INT_CONST ',' INT_CONST '>' ';' { 266 | $$ = grammar_syntax_parser->make_template_field_node(*$3, $5, $7); 267 | } 268 | | 269 | TEMPLATE '<' IDENTIFIER ',' INT_CONST '>' ';' { 270 | $$ = grammar_syntax_parser->make_template_field_node(*$3, $5, $5); 271 | } 272 | | 273 | TEMPLATE '<' IDENTIFIER '>' ';' { 274 | $$ = grammar_syntax_parser->make_template_field_node(*$3, 1, 1); 275 | } 276 | ; 277 | 278 | filler: 279 | expression { 280 | $$ = grammar_syntax_parser->make_function_value_filler_node($1); 281 | } 282 | | 283 | filler_function { 284 | $$ = $1; 285 | } 286 | | 287 | STR_CONST { 288 | $$ = grammar_syntax_parser->make_const_string_node(*$1); 289 | } 290 | ; 291 | 292 | filler_function: 293 | IDENTIFIER '(' IDENTIFIER ')' { 294 | $$ = grammar_syntax_parser->make_node_filler_node(*$3, *$1); 295 | if($$ == nullptr) { 296 | yyerror(("function \"" + *$1 + "\" does not exist").c_str()); 297 | YYABORT; 298 | } 299 | } 300 | ; 301 | 302 | expression: 303 | INT_CONST { 304 | $$ = grammar_syntax_parser->make_const_value_node($1); 305 | } 306 | | 307 | IDENTIFIER { 308 | $$ = grammar_syntax_parser->make_node_value_node(*$1); 309 | } 310 | | 311 | '(' expression ')' { 312 | $$ = $2; 313 | } 314 | | 315 | expression_func '+' expression_func { 316 | $$ = grammar_syntax_parser->make_binary_function_value_node($1, $3); 317 | } 318 | | 319 | expression_func '-' expression_func { 320 | $$ = grammar_syntax_parser->make_binary_function_value_node($1, $3); 321 | } 322 | | 323 | expression_func '/' expression_func { 324 | $$ = grammar_syntax_parser->make_binary_function_value_node($1, $3); 325 | } 326 | | 327 | expression_func '*' expression_func { 328 | $$ = grammar_syntax_parser->make_binary_function_value_node($1, $3); 329 | } 330 | ; 331 | 332 | expression_func: 333 | IDENTIFIER '(' IDENTIFIER ')' { 334 | $$ = grammar_syntax_parser->make_node_value_function_node(*$3, *$1); 335 | if($$ == nullptr) { 336 | yyerror(("function \"" + *$1 + "\" does not exist").c_str()); 337 | YYABORT; 338 | } 339 | } 340 | | 341 | expression { 342 | $$ = $1; 343 | } 344 | ; 345 | 346 | %% 347 | 348 | -------------------------------------------------------------------------------- /parser/syntax.lex: -------------------------------------------------------------------------------- 1 | %{ 2 | 3 | #include 4 | #include 5 | #include "parser/nodes.h" 6 | #include "parser/syntax.h" 7 | #include "parser/syntax_parser.h" 8 | #include "parser/syntax.tab.h" 9 | #define MAX_STR_CONST 1025 10 | 11 | extern int curr_lineno; 12 | extern syntax_parser* grammar_syntax_parser; 13 | extern std::istream *istr; 14 | extern "C" int yylex(); 15 | extern "C" int yyerror(const char *); 16 | 17 | char string_buf[MAX_STR_CONST]; 18 | char *string_buf_ptr; 19 | 20 | std::map hex_map = { 21 | { 'a', 0x0a }, 22 | { 'b', 0x0b }, 23 | { 'c', 0x0c }, 24 | { 'd', 0x0d }, 25 | { 'e', 0x0e }, 26 | { 'f', 0x0f } 27 | }; 28 | 29 | int convert_hex(char input) { 30 | if(input <= '9') 31 | return input - '0'; 32 | return hex_map[tolower(input)]; 33 | } 34 | 35 | #define CHECK_STRLEN \ 36 | if(string_buf_ptr == string_buf + MAX_STR_CONST - 1) { \ 37 | yylval.error_msg = "String constant too long"; \ 38 | BEGIN(STR_LITERAL_ERR); \ 39 | return ERROR; \ 40 | } 41 | 42 | #define YY_USER_ACTION yylloc.first_line = yylloc.last_line = yylineno; 43 | 44 | #undef YY_INPUT 45 | #define YY_INPUT(buf,result,max_size) \ 46 | istr->read( (char*)buf, max_size); \ 47 | result = istr->gcount(); 48 | 49 | 50 | %} 51 | 52 | %option yylineno 53 | %option nounput 54 | 55 | CHARACTER [a-zA-Z_-] 56 | DIGIT [0-9] 57 | NUMBER {DIGIT}+ 58 | HEX_DIGIT ({DIGIT}|[abcdef]) 59 | BRACES ("{"|"}") 60 | PARENS ("("|")") 61 | IDENTIFIER {CHARACTER}({CHARACTER}|{DIGIT})* 62 | OPERATOR ("+"|"-"|"*"|"/") 63 | 64 | %x SINGLE_COMMENT 65 | %x STR_LITERAL 66 | %x STR_LITERAL_ERR 67 | 68 | /* Actual syntax */ 69 | 70 | %% 71 | 72 | "#" { BEGIN(SINGLE_COMMENT); } 73 | [^\n]+ // Eat 74 | \n { BEGIN(INITIAL); curr_lineno++; } 75 | 76 | "\"" { 77 | string_buf_ptr = string_buf; 78 | BEGIN(STR_LITERAL); 79 | } 80 | "\"" { 81 | BEGIN(INITIAL); 82 | *string_buf_ptr = 0; 83 | yylval.symbol = grammar_syntax_parser->make_string(string_buf, string_buf_ptr); 84 | return STR_CONST; 85 | } 86 | "\\x"{HEX_DIGIT}{2} { 87 | CHECK_STRLEN; 88 | *string_buf_ptr++ = ((convert_hex(yytext[2])) << 4) | convert_hex(yytext[3]); 89 | } 90 | "\\n" { CHECK_STRLEN; *string_buf_ptr++ = '\n'; } 91 | "\\b" { CHECK_STRLEN; *string_buf_ptr++ = '\b'; } 92 | "\\f" { CHECK_STRLEN; *string_buf_ptr++ = '\f'; } 93 | "\\t" { CHECK_STRLEN; *string_buf_ptr++ = '\t'; } 94 | "\\\\" { CHECK_STRLEN; *string_buf_ptr++ = '\\'; } 95 | "\\\"" { CHECK_STRLEN; *string_buf_ptr++ = '"'; } 96 | <> { 97 | yylval.error_msg = "EOF in string constant"; 98 | BEGIN(INITIAL); 99 | return ERROR; 100 | } 101 | \n { 102 | curr_lineno++; 103 | yylval.error_msg = "Unterminated string constant"; 104 | BEGIN(INITIAL); 105 | return ERROR; 106 | } 107 | \0 { 108 | yylval.error_msg = "String contains null character"; 109 | BEGIN(STR_LITERAL_ERR); 110 | return ERROR; 111 | } 112 | "\\\n" { CHECK_STRLEN; *string_buf_ptr++ = '\n'; curr_lineno++; } 113 | "\\". { CHECK_STRLEN; *string_buf_ptr++ = yytext[1]; } 114 | [^\\\n\"\0]+ { 115 | const char* yy_ptr = yytext; 116 | if(yyleng > (MAX_STR_CONST - 1) - (string_buf_ptr - string_buf)) { 117 | yylval.error_msg = "String constant too long"; 118 | BEGIN(STR_LITERAL_ERR); 119 | return ERROR; 120 | } 121 | while(*yy_ptr) 122 | *string_buf_ptr++ = *yy_ptr++; 123 | } 124 | 125 | ["\n] { BEGIN(INITIAL); } 126 | "\\\"" // Consume 127 | \\. // Consume 128 | [^\"\\\n] // Consume 129 | 130 | "templates" { return TEMPLATES; } 131 | "template" { return TEMPLATE; } 132 | "str_block" { return STR_BLOCK; } 133 | "var_block" { return VAR_BLOCK; } 134 | "choice" { return CHOICE_FIELD; } 135 | "auto" { return AUTO_FIELD; } 136 | "bitfield" { return BITFIELD; } 137 | "multi_bit" { return COMPOUND_BITFIELD; } 138 | "block" { return BLOCK; } 139 | "multi_block" { return COMPOUND_BLOCK; } 140 | "<" { return yytext[0]; } 141 | ">" { return yytext[0]; } 142 | ";" { return yytext[0]; } 143 | "," { return yytext[0]; } 144 | "=" { return yytext[0]; } 145 | {BRACES} { return yytext[0]; } 146 | {PARENS} { return yytext[0]; } 147 | {OPERATOR} { return yytext[0]; } 148 | "0x"{HEX_DIGIT}+ { 149 | yylval.int_val = strtol(yytext + 2, nullptr, 16); 150 | return INT_CONST; 151 | } 152 | {NUMBER} { 153 | yylval.int_val = atoi(yytext); 154 | return INT_CONST; 155 | } 156 | {IDENTIFIER} { 157 | yylval.symbol = grammar_syntax_parser->make_string(yytext); 158 | return IDENTIFIER; 159 | } 160 | [ \t\f\v\r] // consume whitespace 161 | \n { curr_lineno++; } 162 | . { yyterminate(); } 163 | 164 | %% 165 | -------------------------------------------------------------------------------- /src/bitfield.cpp: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #include 31 | #include 32 | #include "bitfield.h" 33 | #include "utils.h" 34 | #include "exceptions.h" 35 | 36 | void compound_bitfield_impl::set(size_t index, value_type value) 37 | { 38 | throw not_implemented(); 39 | } 40 | 41 | auto compound_bitfield_impl::get(size_t index) const -> value_type 42 | { 43 | value_type result{}; 44 | size_t i = index * 8, end = i + 8; 45 | while(i < end) { 46 | result = (result << 1) | data[i++]; 47 | } 48 | return result; 49 | } 50 | 51 | size_t compound_bitfield_impl::size() const 52 | { 53 | return data.size() / 8; 54 | } 55 | 56 | size_t compound_bitfield_impl::field_count() const 57 | { 58 | return fields.size(); 59 | } 60 | 61 | void compound_bitfield_impl::prepare(generation_context &) 62 | { 63 | if(data.size() % 8 != 0) 64 | throw invalid_field_size(); 65 | size_t global_index = 0; 66 | for(const auto &f : fields) { 67 | size_t index = 0; 68 | while(index < f.size()) { 69 | data[global_index + index] = f[index]; 70 | index++; 71 | } 72 | global_index += index; 73 | } 74 | } 75 | 76 | auto compound_bitfield_impl::dependent_fields() const -> dependents_type 77 | { 78 | dependents_type output; 79 | transform( 80 | fields.begin(), 81 | fields.end(), 82 | std::back_inserter(output), 83 | std::mem_fn(&field::id) 84 | ); 85 | return output; 86 | } 87 | 88 | void compound_bitfield_impl::accept_visitor(const visitor_type& visitor) const 89 | { 90 | for(const auto &f : fields) { 91 | f.accept_visitor(visitor); 92 | } 93 | } 94 | 95 | auto compound_bitfield_impl::fill_from_buffer(buffer_iterator start, buffer_iterator end) 96 | -> buffer_iterator 97 | { 98 | size_t index{}, total = size(); 99 | if(std::distance(start, end) < static_cast(total)) 100 | throw not_enough_data(); 101 | while(index < total) { 102 | set(index++, *start++); 103 | } 104 | return start; 105 | } -------------------------------------------------------------------------------- /src/choice_field.cpp: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #include 31 | #include "choice_field.h" 32 | #include "generation_context.h" 33 | #include "utils.h" 34 | 35 | 36 | void choice_field_impl::set(size_t index, value_type value) 37 | { 38 | #ifdef FUZZER_DEBUG 39 | assert(current_choice != nullptr); 40 | #endif 41 | (*current_choice)[index] = value; 42 | } 43 | 44 | auto choice_field_impl::get(size_t index) const -> value_type 45 | { 46 | #ifdef FUZZER_DEBUG 47 | assert(current_choice != nullptr); 48 | #endif 49 | return (*current_choice)[index]; 50 | } 51 | 52 | size_t choice_field_impl::size() const 53 | { 54 | return current_choice->size(); 55 | } 56 | 57 | void choice_field_impl::prepare(generation_context &ctx) 58 | { 59 | std::uniform_int_distribution dist(0, choices.size() - 1); 60 | current_choice = &choices[dist(ctx.get_random_generator())]; 61 | current_choice->prepare(ctx); 62 | current_choice->fill(ctx); 63 | } 64 | 65 | auto choice_field_impl::dependent_fields() const -> dependents_type 66 | { 67 | return dependents; 68 | } 69 | -------------------------------------------------------------------------------- /src/command_parser.cpp: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #include 31 | #include 32 | #include 33 | #include "command_parser.h" 34 | 35 | 36 | 37 | command_parser::command_parser(const std::string &input) 38 | { 39 | std::tie(application, arguments, replacement_index) = split_cmd(input); 40 | } 41 | 42 | auto command_parser::generate_template(const std::string &file_name) const 43 | -> std::tuple 44 | { 45 | arguments_type args = arguments; 46 | args[replacement_index] = file_name; 47 | return std::make_tuple(application, args); 48 | } 49 | 50 | auto command_parser::split_cmd(const std::string &cmd) -> std::tuple 51 | { 52 | std::istringstream input(cmd); 53 | arguments_type args; 54 | std::string function, part; 55 | size_t index = std::numeric_limits::max(); 56 | if(!std::getline(input, function, ' ')) 57 | throw std::runtime_error("no command given"); 58 | while(std::getline(input, part, ' ')) { 59 | if(part == "{%}") 60 | index = args.size(); 61 | args.push_back(part); 62 | } 63 | if(index == std::numeric_limits::max()) { 64 | args.push_back({}); 65 | index = args.size() - 1; 66 | } 67 | return std::make_tuple(std::move(function), std::move(args) , index); 68 | } 69 | -------------------------------------------------------------------------------- /src/compound_field.cpp: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #include 31 | #include "compound_field.h" 32 | #include "exceptions.h" 33 | 34 | compound_field_impl::compound_field_impl() 35 | : last_iterator(indexes.end()), total_size(0) 36 | { 37 | 38 | } 39 | 40 | compound_field_impl::compound_field_impl(const compound_field_impl &f) 41 | : fields(f.fields), last_iterator(indexes.end()), total_size(f.total_size) 42 | { 43 | 44 | } 45 | 46 | compound_field_impl& compound_field_impl::operator=(compound_field_impl f) 47 | { 48 | swap(*this, f); 49 | return *this; 50 | } 51 | 52 | void compound_field_impl::add_field(field child) 53 | { 54 | fields.push_back(std::move(child)); 55 | } 56 | 57 | auto compound_field_impl::find_index(size_t index) const -> indexes_type::const_iterator 58 | { 59 | // prepare must be called before accesing this field 60 | if(last_iterator == indexes.end()) 61 | throw unprepared_field(); 62 | if(index < last_iterator->first) 63 | last_iterator = indexes.begin(); 64 | auto iter = last_iterator; 65 | while(iter != indexes.end() && index >= iter->first) { 66 | last_iterator = iter++; 67 | } 68 | return last_iterator; 69 | } 70 | 71 | void compound_field_impl::prepare(generation_context &) 72 | { 73 | indexes.clear(); 74 | size_t index = 0; 75 | for(auto &child : fields) { 76 | indexes.insert({ index, &child }); 77 | index += child.size(); 78 | } 79 | last_iterator = indexes.begin(); 80 | total_size = index; 81 | } 82 | 83 | void compound_field_impl::set(size_t index, value_type value) 84 | { 85 | auto iter = find_index(index); 86 | (*iter->second)[index - iter->first] = value; 87 | } 88 | 89 | auto compound_field_impl::get(size_t index) const -> value_type 90 | { 91 | auto iter = find_index(index); 92 | return (*iter->second)[index - iter->first]; 93 | } 94 | 95 | size_t compound_field_impl::size() const 96 | { 97 | return total_size; 98 | } 99 | 100 | size_t compound_field_impl::field_count() const 101 | { 102 | return fields.size(); 103 | } 104 | 105 | void compound_field_impl::accept_visitor(const visitor_type& visitor) const 106 | { 107 | for(const auto &f : fields) { 108 | f.accept_visitor(visitor); 109 | } 110 | } 111 | 112 | auto compound_field_impl::fill_from_buffer(buffer_iterator start, buffer_iterator end) -> buffer_iterator 113 | { 114 | for(auto &f : fields) 115 | start = f.fill_from_buffer(start, end); 116 | return start; 117 | } 118 | 119 | auto compound_field_impl::dependent_fields() const -> dependents_type 120 | { 121 | dependents_type output; 122 | transform( 123 | fields.begin(), 124 | fields.end(), 125 | std::back_inserter(output), 126 | std::mem_fn(&field::id) 127 | ); 128 | return output; 129 | } 130 | 131 | void compound_field_impl::clear_children() 132 | { 133 | fields.clear(); 134 | } 135 | 136 | void swap(compound_field_impl &lhs, compound_field_impl &rhs) 137 | { 138 | using std::swap; 139 | 140 | swap(lhs.fields, rhs.fields); 141 | swap(lhs.indexes, rhs.indexes); 142 | swap(lhs.last_iterator, rhs.last_iterator); 143 | swap(lhs.total_size, rhs.total_size); 144 | } 145 | -------------------------------------------------------------------------------- /src/const_value_node.cpp: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #include 31 | #include "const_value_node.h" 32 | #include "field.h" 33 | #include "exceptions.h" 34 | 35 | 36 | const_value_node::const_value_node(double value) 37 | : value(value) 38 | { 39 | 40 | } 41 | 42 | double const_value_node::eval(generation_context &) { 43 | return value; 44 | } 45 | 46 | 47 | const_string_node::const_string_node(std::string value) 48 | : value(std::move(value)) 49 | { 50 | 51 | } 52 | 53 | void const_string_node::fill(field &f, generation_context &) 54 | { 55 | if(f.size() < value.size()) 56 | throw invalid_field_size(); 57 | std::copy(value.begin(), value.end(), f.begin()); 58 | } 59 | -------------------------------------------------------------------------------- /src/exceptions.cpp: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #include "exceptions.h" 31 | 32 | const char *invalid_field_size::what() const throw() 33 | { 34 | return "invalid field size"; 35 | } 36 | 37 | const char *not_enough_data::what() const throw() 38 | { 39 | return "not enough data"; 40 | } 41 | 42 | const char *dependency_loop_error::what() const throw() 43 | { 44 | return "dependency loop error"; 45 | } 46 | 47 | const char *parse_error::what() const throw() 48 | { 49 | return "parsing error encountered"; 50 | } 51 | 52 | const char *unprepared_field::what() const throw() 53 | { 54 | return "unprepared field"; 55 | } 56 | 57 | const char *field_cant_be_used_in_response::what() const throw() 58 | { 59 | return "field can't be used in response"; 60 | } 61 | 62 | const char *file_open_exception::what() const throw() 63 | { 64 | return "file open exception"; 65 | } 66 | 67 | const char *not_implemented::what() const throw() 68 | { 69 | return "not implemented"; 70 | } 71 | 72 | const char *constraint_too_soft::what() const throw() 73 | { 74 | return "constraint too soft"; 75 | } 76 | 77 | const char *too_many_constraints::what() const throw() 78 | { 79 | return "too many constraints"; 80 | } 81 | 82 | const char *no_constraints::what() const throw() 83 | { 84 | return "no constraints"; 85 | } 86 | 87 | const char *value_too_large::what() const throw() 88 | { 89 | return "value too large"; 90 | } 91 | 92 | semantic_exception::semantic_exception(size_t line, const std::string &str) 93 | : std::runtime_error("error in line " + std::to_string(line) + ": " + str) 94 | { 95 | 96 | } 97 | 98 | 99 | execution_exception::execution_exception(const std::string &str) 100 | : std::runtime_error("Execution exception: " + str) 101 | { 102 | 103 | } 104 | 105 | ast_field_too_small::ast_field_too_small(size_t line, const std::string &node, const std::string &content) 106 | : semantic_exception(line, node + " too small to hold \"" + content + "\"") 107 | { 108 | 109 | } 110 | 111 | 112 | incorrect_ast_field_size::incorrect_ast_field_size(size_t line, const std::string &node, size_t expected) 113 | : semantic_exception(line, node + " should be " + std::to_string(expected) + " bytes long.") 114 | { 115 | 116 | } 117 | 118 | cant_deduct_field_type::cant_deduct_field_type(size_t line, const std::string &node) 119 | : semantic_exception(line, "cannot deduce type for \"" + node + "\" field") 120 | { 121 | 122 | } 123 | -------------------------------------------------------------------------------- /src/executer.cpp: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #ifndef WIN32 31 | #include 32 | #include 33 | #include 34 | #include 35 | #include 36 | #else 37 | #include 38 | #include 39 | #endif // WIN32 40 | #include 41 | #include 42 | #include 43 | #include "executer.h" 44 | #include "field.h" 45 | 46 | executer::executer(const std::string &cmd) 47 | : cmd_template(cmd) 48 | { 49 | 50 | } 51 | 52 | #ifndef WIN32 53 | int redirect_descriptors() 54 | { 55 | int null_fd = open("/dev/null", O_RDWR, 0640); 56 | dup2(null_fd, STDIN_FILENO); 57 | dup2(null_fd, STDOUT_FILENO); 58 | dup2(null_fd, STDERR_FILENO); 59 | return null_fd; 60 | } 61 | 62 | std::string signal_string(int code) 63 | { 64 | static std::map strings = { 65 | { SIGILL, "Illegal instruction" }, 66 | { SIGSEGV, "Segmentation fault" }, 67 | { SIGSTKFLT, "Stack fault" }, 68 | { SIGBUS, "Bus error" }, 69 | { SIGPIPE, "Broken pipe" } 70 | }; 71 | auto iter = strings.find(code); 72 | return (iter == strings.end()) ? "Unknown signal" : iter->second; 73 | } 74 | 75 | auto executer::do_execute(const std::string &file) -> exec_status 76 | { 77 | pid_t pid; 78 | if((pid = fork()) < 0) { 79 | throw execution_exception("fork failed"); 80 | } 81 | if(pid) { 82 | int status = 0; 83 | waitpid(pid, &status, 0); 84 | /* Child was terminated by a signal. */ 85 | if(!WIFEXITED(status) && WIFSIGNALED(status) && WTERMSIG(status) != SIGINT && WTERMSIG(status) != SIGALRM) { 86 | if(WTERMSIG(status) == SIGUSR2) 87 | throw execution_exception("executing application failed"); 88 | else { 89 | return exec_status::killed_by_signal; 90 | } 91 | } 92 | else 93 | return exec_status::success; 94 | } 95 | else { 96 | int null_fd = redirect_descriptors(); 97 | // args stuff 98 | std::string app; 99 | command_parser::arguments_type args; 100 | std::tie(app, args) = cmd_template.generate_template(file); 101 | std::vector exec_args(args.size() + 2); 102 | std::transform(args.begin(), args.end(), exec_args.begin() + 1, std::mem_fn(&std::string::c_str)); 103 | exec_args[0] = app.c_str(); 104 | exec_args.back() = nullptr; 105 | /* When the process runs for more than 7 seconds, it is killed by SIGALRM. */ 106 | alarm(7); 107 | /* If execution fails, the child process kills ifself using SIGUSR2. 108 | * The parent process catches this "exception" and notifies the user. */ 109 | if(execvp(app.c_str(), (char* const*)exec_args.data()) == -1) { 110 | close(null_fd); 111 | kill(getpid(), SIGUSR2); 112 | } 113 | close(null_fd); 114 | alarm(0); 115 | exit(0); 116 | } 117 | // should never get here 118 | return exec_status::failed; 119 | } 120 | 121 | #else // WIN32 122 | 123 | bool is_fatal_exception(DWORD code) 124 | { 125 | static std::set ex_codes = { 126 | EXCEPTION_ACCESS_VIOLATION, 127 | EXCEPTION_STACK_OVERFLOW, 128 | EXCEPTION_ARRAY_BOUNDS_EXCEEDED, 129 | EXCEPTION_ILLEGAL_INSTRUCTION, 130 | EXCEPTION_STACK_OVERFLOW 131 | }; 132 | return ex_codes.count(code); 133 | } 134 | 135 | bool wait_for_exception(EXCEPTION_RECORD &ex) 136 | { 137 | bool ex_thrown = false; 138 | DEBUG_EVENT de; 139 | while(!ex_thrown) { 140 | if(WaitForDebugEvent(&de, (DWORD)100)) { 141 | switch(de.dwDebugEventCode) { 142 | case EXCEPTION_DEBUG_EVENT: 143 | if(is_fatal_exception(de.u.Exception.ExceptionRecord.ExceptionCode)) 144 | ex_thrown = true; 145 | break; 146 | case EXIT_PROCESS_DEBUG_EVENT: 147 | return false; 148 | default: 149 | ContinueDebugEvent (de.dwProcessId, de.dwThreadId, DBG_CONTINUE); 150 | break; 151 | } 152 | } 153 | else 154 | ContinueDebugEvent (de.dwProcessId, de.dwThreadId, DBG_CONTINUE); 155 | } 156 | /* Exception caught! */ 157 | ex = de.u.Exception.ExceptionRecord; 158 | return ex_thrown; 159 | } 160 | 161 | HANDLE set_startup_info(STARTUPINFOA &info) 162 | { 163 | info = {}; 164 | info.cb = sizeof(STARTUPINFOA); 165 | info.dwFlags = STARTF_USESTDHANDLES; 166 | HANDLE pout = CreateFile((LPCTSTR)"null", GENERIC_WRITE, 0, 0, OPEN_ALWAYS, FILE_ATTRIBUTE_NORMAL, 0); 167 | info.hStdInput = pout; 168 | info.hStdOutput = pout; 169 | info.hStdError = pout; 170 | return pout; 171 | } 172 | 173 | auto executer::do_execute(const std::string &file) -> exec_status 174 | { 175 | exec_status result = exec_status::success; 176 | STARTUPINFOA siStartupInfo; 177 | PROCESS_INFORMATION piProcessInfo{}; 178 | HANDLE handle = set_startup_info(siStartupInfo); 179 | // args stuff 180 | std::string app, arguments; 181 | command_parser::arguments_type args; 182 | std::tie(app, args) = cmd_template.generate_template(file); 183 | for(auto it = args.begin(); it != args.end(); it++) { 184 | arguments += *it; 185 | if(it + 1 != args.end()) 186 | arguments.push_back(' '); 187 | } 188 | 189 | if(!CreateProcessA(app.c_str(), (LPTSTR)arguments.c_str(), 0, 0, 0, NORMAL_PRIORITY_CLASS | DEBUG_PROCESS, 0, 0, &siStartupInfo, &piProcessInfo)) { 190 | CloseHandle(handle); 191 | throw execution_exception("executing application failed: " + GetLastError()); 192 | } 193 | EXCEPTION_RECORD ex_info; 194 | if(wait_for_exception(ex_info)) { 195 | result = exec_status::killed_by_signal; 196 | } 197 | CloseHandle(handle); 198 | return result; 199 | } 200 | #endif 201 | -------------------------------------------------------------------------------- /src/field.cpp: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #include 31 | #include "field.h" 32 | #include "field_impl.h" 33 | #include "endianness.h" 34 | #include "exceptions.h" 35 | #include "field_mapper.h" 36 | #include "generation_context.h" 37 | 38 | std::atomic field::global_id(1); 39 | 40 | field::identifier_type field::generate_id() 41 | { 42 | return global_id++; 43 | } 44 | 45 | field::field(filler_type filler, unique_impl impl) 46 | : impl(std::move(impl)), filler(std::move(filler)), identifier(global_id++) 47 | { 48 | 49 | } 50 | 51 | field::field(identifier_type id, filler_type filler, unique_impl impl) 52 | : impl(std::move(impl)), filler(std::move(filler)), identifier(id) 53 | { 54 | if(identifier == invalid_id) 55 | identifier = global_id++; 56 | } 57 | 58 | field::field(const field &rhs) 59 | : impl(rhs.impl ? rhs.impl->clone() : nullptr), filler(rhs.filler), 60 | identifier(rhs.identifier) 61 | { 62 | 63 | } 64 | 65 | field::field(field &&rhs) noexcept 66 | { 67 | swap(*this, rhs); 68 | } 69 | 70 | field& field::operator=(field rhs) 71 | { 72 | swap(*this, rhs); 73 | return *this; 74 | } 75 | 76 | size_t field::size() const 77 | { 78 | return impl->size(); 79 | } 80 | 81 | size_t field::field_count() const 82 | { 83 | return impl->field_count(); 84 | } 85 | 86 | auto field::begin() -> iterator 87 | { 88 | return *impl; 89 | } 90 | 91 | auto field::begin() const -> const_iterator 92 | { 93 | return *impl; 94 | } 95 | 96 | auto field::end() -> iterator 97 | { 98 | return { *impl, impl->size() }; 99 | } 100 | 101 | auto field::end() const -> const_iterator 102 | { 103 | return { *impl, impl->size() }; 104 | } 105 | 106 | auto field::operator[](size_t index) -> dereference_helper 107 | { 108 | return *(begin() + index); 109 | } 110 | 111 | auto field::operator[](size_t index) const -> dereference_helper 112 | { 113 | return *(begin() + index); 114 | } 115 | 116 | void field::prepare(generation_context &context) 117 | { 118 | impl->prepare(context); 119 | } 120 | 121 | void field::fill(generation_context &context) 122 | { 123 | if(filler) 124 | filler->fill(*this, context); 125 | } 126 | 127 | auto field::fill_from_buffer(buffer_iterator start, buffer_iterator end) -> buffer_iterator 128 | { 129 | return impl->fill_from_buffer(start, end); 130 | } 131 | 132 | void field::set_value(int64_t value) 133 | { 134 | if(value == 0.0) 135 | std::fill(begin(), end(), 0); 136 | else 137 | impl->set_value(value); 138 | } 139 | 140 | int64_t field::get_value() const 141 | { 142 | return impl->get_value(); 143 | } 144 | 145 | void field::accept_visitor(const visitor_type &visitor) const 146 | { 147 | visitor(*this); 148 | impl->accept_visitor(visitor); 149 | } 150 | 151 | auto field::dependent_fields() const -> dependents_type 152 | { 153 | auto fields = impl->dependent_fields(); 154 | if(filler) { 155 | auto filler_fields = filler->dependent_fields(); 156 | fields.insert(fields.end(), filler_fields.begin(), filler_fields.end()); 157 | } 158 | return fields; 159 | } 160 | 161 | bool operator<(const field &lhs, const field &rhs) 162 | { 163 | return lhs.id() < rhs.id(); 164 | } 165 | 166 | void swap(field &lhs, field &rhs) 167 | { 168 | using std::swap; 169 | swap(lhs.impl, rhs.impl); 170 | swap(lhs.filler, rhs.filler); 171 | swap(lhs.identifier, rhs.identifier); 172 | } 173 | -------------------------------------------------------------------------------- /src/field_impl.cpp: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #include 31 | #include "field_impl.h" 32 | #include "exceptions.h" 33 | 34 | void field_impl::set_value(int64_t value) 35 | { 36 | int index = size() - 1; 37 | while(index >= 0 && value != 0) { 38 | set(index--, static_cast(value) & 0xff); 39 | value >>= 8; 40 | } 41 | } 42 | 43 | int64_t field_impl::get_value() const 44 | { 45 | int64_t val{}; 46 | int end = size() - 1, index = end; 47 | while(index >= 0 && static_cast(end - index) < sizeof(int64_t)) { 48 | val = val | (static_cast(get(index)) << ((end - index) * 8)); 49 | index--; 50 | } 51 | return val; 52 | } 53 | 54 | size_t field_impl::field_count() const 55 | { 56 | return 1; 57 | } 58 | 59 | void field_impl::prepare(generation_context &) 60 | { 61 | 62 | } 63 | 64 | auto field_impl::dependent_fields() const -> dependents_type 65 | { 66 | return { }; 67 | }; 68 | 69 | auto field_impl::fill_from_buffer(buffer_iterator start, buffer_iterator end) -> buffer_iterator 70 | { 71 | throw field_cant_be_used_in_response(); 72 | } -------------------------------------------------------------------------------- /src/field_mapper.cpp: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #include 31 | #include "field_mapper.h" 32 | 33 | field::identifier_type field_mapper::register_field(std::string name) 34 | { 35 | // CHECK 36 | auto iter = str2id.find(name); 37 | if(iter != str2id.end()) { 38 | // this field has already been registered by someone else 39 | if(iter->second.second) 40 | throw std::runtime_error("field \"" + name + "\" already defined"); 41 | else { 42 | iter->second.second = true; 43 | return iter->second.first; 44 | } 45 | } 46 | 47 | auto id = field::generate_id(); 48 | str2id[std::move(name)] = { id , true }; 49 | return id; 50 | } 51 | 52 | void field_mapper::register_field(field::identifier_type id, const field &f) 53 | { 54 | id2field.insert({ id, f }); 55 | } 56 | 57 | field::identifier_type field_mapper::find_register_field_name(const std::string &fname) 58 | { 59 | auto iter = str2id.find(fname); 60 | if(iter == str2id.end()) 61 | iter = str2id.insert({ fname, { field::generate_id(), false } }).first; 62 | return iter->second.first; 63 | } 64 | 65 | void field_mapper::identify_fields(const field &root) 66 | { 67 | using std::placeholders::_1; 68 | 69 | root.accept_visitor( 70 | std::bind(&field_mapper::visit, this, _1) 71 | ); 72 | } 73 | 74 | void field_mapper::visit(const field &f) 75 | { 76 | id2field.insert({ f.id(), f }); 77 | } 78 | 79 | const field& field_mapper::find_field(field::identifier_type id) const 80 | { 81 | return id2field.at(id); 82 | } 83 | 84 | auto field_mapper::find_field_name(const std::string &fname) const -> field::identifier_type 85 | { 86 | return str2id.at(fname).first; 87 | } 88 | -------------------------------------------------------------------------------- /src/field_serializer.cpp: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #include 31 | #include "field_serializer.h" 32 | #include "topological_sorter.h" 33 | #include "generation_context.h" 34 | 35 | field_serializer::field_serializer(field root, size_t num_threads, size_t max_fields) 36 | : max_fields(max_fields), running(true) 37 | { 38 | for(auto i = size_t(); i < num_threads; ++i) 39 | threads.emplace_back(&field_serializer::thread_proc, this, root); 40 | } 41 | 42 | field_serializer::~field_serializer() 43 | { 44 | if(running) 45 | stop(); 46 | for(auto &t : threads) 47 | t.join(); 48 | } 49 | 50 | void field_serializer::stop() 51 | { 52 | running = false; 53 | pop_cond.notify_all(); 54 | push_cond.notify_all(); 55 | } 56 | 57 | auto field_serializer::next_field() -> serialization_type 58 | { 59 | std::unique_lock locker(queue_lock); 60 | if(result_queue.empty()) { 61 | push_cond.wait(locker); 62 | // woken up by stop() 63 | if(!running) 64 | return serialization_type(); 65 | } 66 | auto result = std::move(result_queue.front()); 67 | result_queue.pop(); 68 | pop_cond.notify_one(); 69 | return result; 70 | } 71 | 72 | void field_serializer::store_field(serialization_type f) 73 | { 74 | std::unique_lock locker(queue_lock); 75 | if(result_queue.size() >= max_fields) { 76 | pop_cond.wait(locker); 77 | if(!running) 78 | return; 79 | } 80 | result_queue.push(std::move(f)); 81 | push_cond.notify_one(); 82 | } 83 | 84 | void field_serializer::thread_proc(field root) 85 | { 86 | // some seed plx 87 | generation_context ctx{std::random_device()()}; 88 | topological_sorter sorter; 89 | auto ordered = sorter.topological_sort(root); 90 | ctx.get_mapper().identify_fields(root); 91 | while(running) { 92 | for(const auto &i : ordered) { 93 | const_cast(ctx.get_mapper().find_field(i)).prepare(ctx); 94 | const_cast(ctx.get_mapper().find_field(i)).fill(ctx); 95 | } 96 | store_field(serialization_type(root.begin(), root.end())); 97 | } 98 | } 99 | -------------------------------------------------------------------------------- /src/function_value_filler.cpp: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #include "function_value_filler.h" 31 | #include "field.h" 32 | 33 | function_value_filler::function_value_filler(unique_value value) 34 | : value(std::move(value)) 35 | { 36 | 37 | } 38 | 39 | auto function_value_filler::dependent_fields() const -> dependents_type 40 | { 41 | return value->dependent_fields(); 42 | } 43 | 44 | void function_value_filler::fill(field &f, generation_context &ctx) 45 | { 46 | f.set_value(value->eval(ctx)); 47 | } 48 | -------------------------------------------------------------------------------- /src/functions/constraints.cpp: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #include "functions/constraints.h" 31 | #include "parser/nodes.h" 32 | #include "exceptions.h" 33 | #include "block_field.h" 34 | #include "utils.h" 35 | 36 | std::unique_ptr function_constraint::field_impl_from_constraint() const 37 | { 38 | throw constraint_too_soft(); 39 | } 40 | 41 | 42 | required_size_constraint::required_size_constraint(size_t required) 43 | : required(required) 44 | { 45 | 46 | } 47 | 48 | void required_size_constraint::check(const grammar::field_node &f) const 49 | { 50 | if(f.min_size() != required || f.max_size() != required) 51 | throw incorrect_ast_field_size(f.get_line_number(), f.to_string(), required); 52 | } 53 | 54 | std::unique_ptr required_size_constraint::field_impl_from_constraint() const 55 | { 56 | return make_unique(required); 57 | } 58 | -------------------------------------------------------------------------------- /src/functions/crc.cpp: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #include 31 | #include "functions/crc.h" 32 | #include "field.h" 33 | #include "field_mapper.h" 34 | 35 | crc32_function::crc32_function(identifier_type id) 36 | : unary_field_function(id) 37 | { 38 | 39 | } 40 | 41 | double crc32_function::apply(const field &input_field) 42 | { 43 | uint32_t crc = 0; 44 | static uint32_t crc_table[] = { 45 | 0x4DBDF21C, 0x500AE278, 0x76D3D2D4, 0x6B64C2B0, 46 | 0x3B61B38C, 0x26D6A3E8, 0x000F9344, 0x1DB88320, 47 | 0xA005713C, 0xBDB26158, 0x9B6B51F4, 0x86DC4190, 48 | 0xD6D930AC, 0xCB6E20C8, 0xEDB71064, 0xF0000000 49 | }; 50 | 51 | for(auto &&i : input_field) { 52 | crc = (crc >> 4) ^ crc_table[(crc ^ i) & 0x0F]; 53 | crc = (crc >> 4) ^ crc_table[(crc ^ (i >> 4)) & 0x0F]; 54 | } 55 | 56 | return crc; 57 | } 58 | -------------------------------------------------------------------------------- /src/functions/hashing.cpp: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #include 31 | #include 32 | #include 33 | #include 34 | #include 35 | #include 36 | #include "functions/hashing.h" 37 | #include "field.h" 38 | #include "exceptions.h" 39 | #include "field_mapper.h" 40 | #include "utils.h" 41 | 42 | md5_function::md5_function(identifier_type id) 43 | : unary_field_filler_function(id) 44 | { 45 | 46 | } 47 | 48 | void md5_function::apply(const field &input_field, field &output_field) 49 | { 50 | #ifdef FUZZER_DEBUG 51 | assert(output_field.size() == MD5_DIGEST_LENGTH); 52 | #endif 53 | std::array buffer; 54 | const std::vector input(input_field.begin(), input_field.end()); 55 | MD5(input.data(), input.size(), buffer.data()); 56 | std::copy(buffer.begin(), buffer.end(), output_field.begin()); 57 | } 58 | 59 | auto md5_function::get_constraints() -> const std::array & 60 | { 61 | static const std::array constraints{ 62 | { make_unique(MD5_DIGEST_LENGTH) } 63 | }; 64 | return constraints; 65 | } 66 | 67 | 68 | sha1_function::sha1_function(identifier_type id) 69 | : unary_field_filler_function(id) 70 | { 71 | 72 | } 73 | 74 | void sha1_function::apply(const field &input_field, field &output_field) 75 | { 76 | #ifdef FUZZER_DEBUG 77 | assert(output_field.size() == SHA_DIGEST_LENGTH); 78 | #endif 79 | std::array buffer; 80 | const std::vector input(input_field.begin(), input_field.end()); 81 | SHA1(input.data(), input.size(), buffer.data()); 82 | std::copy(buffer.begin(), buffer.end(), output_field.begin()); 83 | } 84 | 85 | auto sha1_function::get_constraints() -> const std::array & 86 | { 87 | static const std::array constraints{ 88 | { make_unique(SHA_DIGEST_LENGTH) } 89 | }; 90 | return constraints; 91 | } 92 | 93 | -------------------------------------------------------------------------------- /src/functions/random.cpp: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #include 31 | #include 32 | #include 33 | #include "functions/random.h" 34 | #include "field.h" 35 | #include "generation_context.h" 36 | 37 | void random_function::fill(field &f, generation_context &ctx) 38 | { 39 | std::uniform_int_distribution generator(0, 0xff); 40 | std::generate( 41 | f.begin(), 42 | f.end(), 43 | [&]{ return generator(ctx.get_random_generator()); } 44 | ); 45 | } 46 | 47 | void bitrandom_function::fill(field &f, generation_context &ctx) 48 | { 49 | std::uniform_int_distribution generator(0, 1); 50 | std::generate( 51 | f.begin(), 52 | f.end(), 53 | [&]{ return generator(ctx.get_random_generator()); } 54 | ); 55 | } 56 | -------------------------------------------------------------------------------- /src/generation_context.cpp: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #include "generation_context.h" 31 | 32 | generation_context::generation_context(random_generator::result_type seed) 33 | : rnd(seed) 34 | { 35 | 36 | } 37 | 38 | field_mapper &generation_context::get_mapper() 39 | { 40 | return mapper; 41 | } 42 | 43 | const field_mapper &generation_context::get_mapper() const 44 | { 45 | return mapper; 46 | } 47 | 48 | auto generation_context::get_random_generator() -> random_generator& 49 | { 50 | return rnd; 51 | } 52 | -------------------------------------------------------------------------------- /src/main.cpp: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2012, Matias Fontanini 3 | * All rights reserved. 4 | * 5 | * Redistribution and use in source and binary forms, with or without 6 | * modification, are permitted provided that the following conditions are 7 | * met: 8 | * 9 | * * Redistributions of source code must retain the above copyright 10 | * notice, this list of conditions and the following disclaimer. 11 | * * Redistributions in binary form must reproduce the above 12 | * copyright notice, this list of conditions and the following disclaimer 13 | * in the documentation and/or other materials provided with the 14 | * distribution. 15 | * 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 | * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 | * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | * 28 | */ 29 | 30 | #ifndef WIN32 31 | #include 32 | #endif 33 | #include 34 | #include 35 | #include 36 | #include 37 | #include 38 | #include "field.h" 39 | #include "parser/syntax_parser.h" 40 | #include "generation_context.h" 41 | #include "topological_sorter.h" 42 | #include "executer.h" 43 | #include "field_serializer.h" 44 | 45 | 46 | std::atomic running(true); 47 | field_serializer* serializer_ptr(nullptr); 48 | 49 | field parse_file(const std::string &template_file) 50 | { 51 | std::ifstream input_stream(template_file); 52 | if(!input_stream) 53 | throw std::runtime_error("file \"" + template_file + "\" does not exist"); 54 | syntax_parser parser; 55 | parser.parse(input_stream); 56 | 57 | field root_field = std::move(parser.get_root_field()); 58 | 59 | std::vector undefined; 60 | parser.get_mapper().find_non_registered_fields(std::back_inserter(undefined)); 61 | if(!undefined.empty()) { 62 | for(const auto &str : undefined) 63 | std::cout << "field \"" << str << "\" is not defined." << std::endl; 64 | throw parse_error(); 65 | } 66 | 67 | return root_field; 68 | } 69 | 70 | void move_file(const std::string &from, const std::string &to) 71 | { 72 | if(rename(from.c_str(), to.c_str()) == -1) { 73 | std::ifstream from_file(from); 74 | std::ofstream to_file(to); 75 | if(!from_file || !to_file) 76 | throw std::runtime_error("moving file failed"); 77 | to_file << from_file.rdbuf(); 78 | } 79 | } 80 | 81 | void run(const std::string &template_file, const std::string &cmd, 82 | const std::string &file_name, const std::string &output_base) 83 | { 84 | executer exec(cmd); 85 | field root = parse_file(template_file); 86 | size_t execution_count{}, crashed_count{}; 87 | field_serializer serializer(std::move(root), 1); 88 | serializer_ptr = &serializer; 89 | while(running) { 90 | field_serializer::serialization_type f = serializer.next_field(); 91 | if(running) { 92 | execution_count++; 93 | if(execution_count % 300 == 0) { 94 | std::cout << "\r[+] Executing test number " << execution_count << ". Crashed: " << crashed_count; 95 | std::cout.flush(); 96 | } 97 | if(exec.execute(f.begin(), f.end(), file_name) == executer::exec_status::killed_by_signal) { 98 | move_file(file_name, output_base + '-' + std::to_string(crashed_count)); 99 | crashed_count++; 100 | if(crashed_count == 10) 101 | break; 102 | } 103 | } 104 | } 105 | } 106 | 107 | void print_usage(char *name) { 108 | std::cout << "sloth fuzzer v" << FUZZER_VERSION << std::endl << std::endl; 109 | std::cout << "Usage: " << name << " [OPTIONS] COMMAND" << std::endl; 110 | std::cout << "\n"; 111 | std::cout << "OPTIONS can be:" << std::endl; 112 | std::cout << "\t-t