diff --git a/libyara/proc/linux.c b/libyara/proc/linux.c index dd824995..b3cf6184 100644 --- a/libyara/proc/linux.c +++ b/libyara/proc/linux.c @@ -51,7 +51,10 @@ typedef struct _YR_PROC_INFO FILE* maps; int page_size; char map_path[PATH_MAX]; - uint64_t map_dmaj, map_dmin, map_ino, map_offset; + uint64_t map_dmaj; + uint64_t map_dmin; + uint64_t map_ino; + uint64_t map_offset; } YR_PROC_INFO; static int page_size = -1; @@ -137,7 +140,7 @@ int _yr_process_detach(YR_PROC_ITERATOR_CTX* context) YR_API const uint8_t* yr_process_fetch_memory_block_data(YR_MEMORY_BLOCK* block) { const uint8_t* result = NULL; - uint64_t *pagemap = NULL; + uint64_t* pagemap = NULL; YR_PROC_ITERATOR_CTX* context = (YR_PROC_ITERATOR_CTX*) block->context; YR_PROC_INFO* proc_info = (YR_PROC_INFO*) context->proc_info; @@ -149,20 +152,21 @@ YR_API const uint8_t* yr_process_fetch_memory_block_data(YR_MEMORY_BLOCK* block) context->buffer_size = 0; } - int fd = -2; /* Assume mapping not connected with a file */ + int fd = -2; // Assume mapping not connected with a file. + if (strlen(proc_info->map_path) > 0 && proc_info->map_dmaj != 0 && proc_info->map_ino != 0) { struct stat st; fd = open(proc_info->map_path, O_RDONLY); + if (fd < 0) { - /* file does not exist. */ - fd = -1; + fd = -1; // File does not exist. } else if (fstat(fd, &st) < 0) { - /* Why should stat fail after file open? Treat like missing. */ + // Why should stat fail after file open? Treat like missing. close(fd); fd = -1; } @@ -171,20 +175,20 @@ YR_API const uint8_t* yr_process_fetch_memory_block_data(YR_MEMORY_BLOCK* block) (minor(st.st_dev) != proc_info->map_dmin) || (st.st_ino != proc_info->map_ino)) { - /* Wrong file, may have been replaced. Treat like missing. */ + // Wrong file, may have been replaced. Treat like missing. close(fd); fd = -1; } else if (st.st_size < proc_info->map_offset + block->size) { - /* Mapping extends past end of file. Treat like missing. */ + // Mapping extends past end of file. Treat like missing. close(fd); fd = -1; } else if ((st.st_mode & S_IFMT) != S_IFREG) { - /* Correct filesystem object, but not a regular file. Treat like - * uninitialized mapping. */ + // Correct filesystem object, but not a regular file. Treat like + // uninitialized mapping. close(fd); fd = -2; } @@ -222,8 +226,8 @@ YR_API const uint8_t* yr_process_fetch_memory_block_data(YR_MEMORY_BLOCK* block) goto _exit; } - /* If mapping can't be accessed through the filesystem, read everything from - * target process VM. */ + // If mapping can't be accessed through the filesystem, read everything from + // target process VM. if (fd == -1) { if (pread( @@ -253,12 +257,14 @@ YR_API const uint8_t* yr_process_fetch_memory_block_data(YR_MEMORY_BLOCK* block) for (uint64_t i = 0; i < block->size / page_size; i++) { - if (pagemap[i] >> 61 == 0) { + if (pagemap[i] >> 61 == 0) + { continue; } - /* Overwrite our mapping if the page is present, file-backed, or - * swap-backed and if it differs from our mapping. */ + // Overwrite our mapping if the page is present, file-backed, or + // swap-backed and if it differs from our mapping. uint8_t buffer[page_size]; + if (pread( proc_info->mem_fd, buffer, @@ -267,9 +273,14 @@ YR_API const uint8_t* yr_process_fetch_memory_block_data(YR_MEMORY_BLOCK* block) { goto _exit; } - if (memcmp((void*) context->buffer + i * page_size, (void*) buffer, page_size) != 0) + + if (memcmp( + (void*) context->buffer + i * page_size, + (void*) buffer, + page_size) != 0) { - memcpy((void*) context->buffer + i * page_size, (void*) buffer, page_size); + memcpy( + (void*) context->buffer + i * page_size, (void*) buffer, page_size); } } } diff --git a/tests/mapper.c b/tests/mapper.c index 07883fcc..76267daf 100644 --- a/tests/mapper.c +++ b/tests/mapper.c @@ -1,5 +1,33 @@ +/* +Copyright (c) 2021. The YARA Authors. All Rights Reserved. + +Redistribution and use in source and binary forms, with or without modification, +are permitted provided that the following conditions are met: + +1. Redistributions of source code must retain the above copyright notice, this +list of conditions and the following disclaimer. + +2. Redistributions in binary form must reproduce the above copyright notice, +this list of conditions and the following disclaimer in the documentation and/or +other materials provided with the distribution. + +3. Neither the name of the copyright holder nor the names of its contributors +may be used to endorse or promote products derived from this software without +specific prior written permission. + +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND +ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR +ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON +ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +*/ + #include -#include #include #include #include @@ -32,6 +60,7 @@ char* map_file(char* path) int main(int argc, char** argv) { char* buf; + if (argc < 2) { fprintf(stderr, "no argument\n"); @@ -41,6 +70,7 @@ int main(int argc, char** argv) { if (argc < 3) exit(1); + printf("%s: %s %s\n", argv[0], argv[1], argv[2]); buf = map_file(argv[2]); } @@ -48,9 +78,14 @@ int main(int argc, char** argv) { if (argc < 3) exit(1); + printf("%s: %s %s\n", argv[0], argv[1], argv[2]); buf = map_file(argv[2]); - for (int i = 0; i < sizeof(str) - 1; i++) buf[i] = str[sizeof(str) - i - 2]; + + for (int i = 0; i < sizeof(str) - 1; i++) + { + buf[i] = str[sizeof(str) - i - 2]; + } } else { diff --git a/tests/test-api.c b/tests/test-api.c index 78f2c543..24e46077 100644 --- a/tests/test-api.c +++ b/tests/test-api.c @@ -1,3 +1,32 @@ +/* +Copyright (c) 2021. The YARA Authors. All Rights Reserved. + +Redistribution and use in source and binary forms, with or without modification, +are permitted provided that the following conditions are met: + +1. Redistributions of source code must retain the above copyright notice, this +list of conditions and the following disclaimer. + +2. Redistributions in binary form must reproduce the above copyright notice, +this list of conditions and the following disclaimer in the documentation and/or +other materials provided with the distribution. + +3. Neither the name of the copyright holder nor the names of its contributors +may be used to endorse or promote products derived from this software without +specific prior written permission. + +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND +ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR +ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON +ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +*/ + #include #include #include @@ -57,7 +86,6 @@ void test_disabled_rules() yr_finalize(); } - const char* _include_callback( const char* include_name, const char* calling_rule_filename, @@ -70,7 +98,6 @@ const char* _include_callback( return NULL; } - void test_include_callback() { YR_COMPILER* compiler = NULL; @@ -103,7 +130,6 @@ void test_include_callback() yr_finalize(); } - void test_file_descriptor() { YR_COMPILER* compiler = NULL; @@ -205,7 +231,6 @@ void test_max_string_per_rules() yr_finalize(); } - int test_max_match_data_callback( YR_SCAN_CONTEXT* context, int message, @@ -272,7 +297,6 @@ void test_max_match_data() yr_finalize(); } - void test_save_load_rules() { YR_COMPILER* compiler = NULL; @@ -350,7 +374,6 @@ void test_save_load_rules() yr_finalize(); } - void test_scanner() { const char* buf = "dummy"; @@ -385,7 +408,6 @@ void test_scanner() yr_compiler_define_boolean_variable(compiler, "bool_var", 0); yr_compiler_define_string_variable(compiler, "str_var", ""); - if (yr_compiler_define_string_variable(compiler, "str_var", "") != ERROR_DUPLICATED_EXTERNAL_VARIABLE) { @@ -574,7 +596,6 @@ void test_issue_834() yr_finalize(); } - void ast_callback( const YR_RULE* rule, const char* string_identifier, @@ -627,7 +648,6 @@ void test_ast_callback() yr_finalize(); } - void stats_for_rules(const char* rules_str, YR_RULES_STATS* stats) { YR_COMPILER* compiler = NULL; @@ -662,7 +682,6 @@ void stats_for_rules(const char* rules_str, YR_RULES_STATS* stats) yr_finalize(); } - void test_rules_stats() { YR_RULES_STATS stats; @@ -749,7 +768,6 @@ void test_rules_stats() assert_true_expr(stats.ac_root_match_list_length == 0); } - void test_issue_920() { const char* rules_str = "\ @@ -788,8 +806,8 @@ void test_issue_920() yr_finalize(); } - -void test_runtime_warnings() { +void test_runtime_warnings() +{ // This rule should never match since it will hit the maximum number of // matches (see YR_MAX_STRING_MATCHES) and a warning will be issued, and any // further matches no longer count. @@ -810,12 +828,14 @@ void test_runtime_warnings() { yr_initialize(); - if (yr_compiler_create(&compiler) != ERROR_SUCCESS) { + if (yr_compiler_create(&compiler) != ERROR_SUCCESS) + { perror("yr_compiler_create"); exit(EXIT_FAILURE); } - if (yr_compiler_add_string(compiler, rules_str, NULL) != ERROR_SUCCESS) { + if (yr_compiler_add_string(compiler, rules_str, NULL) != ERROR_SUCCESS) + { yr_compiler_destroy(compiler); perror("yr_compiler_add_string"); exit(EXIT_FAILURE); @@ -830,7 +850,14 @@ void test_runtime_warnings() { yr_compiler_destroy(compiler); - if (yr_rules_scan_file(rules, prefix_top_srcdir("tests/data/x.txt"), 0, count, &counters, 0) != ERROR_SUCCESS) { + if (yr_rules_scan_file( + rules, + prefix_top_srcdir("tests/data/x.txt"), + 0, + count, + &counters, + 0) != ERROR_SUCCESS) + { yr_rules_destroy(rules); perror("yr_rules_scan_file"); exit(EXIT_FAILURE); @@ -848,7 +875,14 @@ void test_runtime_warnings() { counters.rules_matching = 0; counters.rules_warning = 0; - if (yr_rules_scan_file(rules, prefix_top_srcdir("tests/data/x.txt"), 0, count, &counters, 0) != ERROR_SUCCESS) { + if (yr_rules_scan_file( + rules, + prefix_top_srcdir("tests/data/x.txt"), + 0, + count, + &counters, + 0) != ERROR_SUCCESS) + { yr_rules_destroy(rules); perror("yr_rules_scan_file"); exit(EXIT_FAILURE); @@ -886,7 +920,8 @@ int main(int argc, char** argv) test_issue_920(); test_runtime_warnings(); - YR_DEBUG_FPRINTF(1, stderr, "} = %d // %s() in %s\n", result, __FUNCTION__, argv[0]); + YR_DEBUG_FPRINTF( + 1, stderr, "} = %d // %s() in %s\n", result, __FUNCTION__, argv[0]); return result; } diff --git a/tests/test-rules.c b/tests/test-rules.c index 857071ad..4a874196 100644 --- a/tests/test-rules.c +++ b/tests/test-rules.c @@ -27,6 +27,7 @@ ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ +#include #include #include #include @@ -35,7 +36,6 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. #include #include #include -#include #if !defined(_WIN32) && !defined(__CYGWIN__) #include @@ -2826,7 +2826,7 @@ void test_tags() #if !defined(_WIN32) || defined(__CYGWIN__) -#define spawn(cmd,rest...) \ +#define spawn(cmd, rest...) \ do \ { \ if ((pid = fork()) == 0) \ @@ -2885,6 +2885,14 @@ void test_process_scan() counters.rules_matching = 0; counters.rules_not_matching = 0; rc = yr_rules_scan_proc(rules, pid, 0, count, &counters, 0); + + switch (rc) + { + case ERROR_COULD_NOT_ATTACH_TO_PROCESS: + fprintf(stderr, "Could not attach to process, ignoring this error\n"); + return; + } + kill(pid, SIGALRM); assert(rc == ERROR_SUCCESS);