diff --git a/CHANGES b/CHANGES index b9d4a32a47..5cd0214d83 100644 --- a/CHANGES +++ b/CHANGES @@ -1,4 +1,22 @@ +3.2.0-dev.106 | 2020-02-24 17:07:10 -0800 + + * ScannedFile: Identify already scanned files by device and inode (Arne Welzel) + + Zeek scripts located on separate filesystems, but sharing the same inode + number leads to scripts not being loaded. The reason is that a `ScannedFile` + is only identified by `st_ino` which is not enough to uniquely identify a + file in a system. + + * GH-808: Add ZEEK_VERSION_NUMBER definition to zeek-config.h (Jon Siwek, Corelight) + + This is the result of (major * 10000 + minor * 100 + patch), for example + 3.1.2 becomes 30102. This definition may be helpful for external code + that requires conditional compilation to support multiple Zeek + versions with differing APIs. + + * Fix CI to checkout right commit of zeek-testing-private (Jon Siwek, Corelight) + 3.2.0-dev.99 | 2020-02-21 21:23:52 -0800 * Update a URL in CI README (Jon Siwek, Corelight) diff --git a/VERSION b/VERSION index 0dfb7d7c59..9d14e14320 100644 --- a/VERSION +++ b/VERSION @@ -1 +1 @@ -3.2.0-dev.99 +3.2.0-dev.106 diff --git a/src/Net.h b/src/Net.h index 25901a78dd..e7b7f3bd7f 100644 --- a/src/Net.h +++ b/src/Net.h @@ -88,20 +88,22 @@ extern iosource::IOSource* current_iosrc; extern iosource::PktDumper* pkt_dumper; // where to save packets // Script file we have already scanned (or are in the process of scanning). -// They are identified by inode number. +// They are identified by device and inode number. struct ScannedFile { + dev_t dev; ino_t inode; int include_level; string name; bool skipped; // This ScannedFile was @unload'd. bool prefixes_checked; // If loading prefixes for this file has been tried. - ScannedFile(ino_t arg_inode, int arg_include_level, const string& arg_name, - bool arg_skipped = false, - bool arg_prefixes_checked = false) - : inode(arg_inode), include_level(arg_include_level), - name(arg_name), skipped(arg_skipped), - prefixes_checked(arg_prefixes_checked) + ScannedFile(dev_t arg_dev, ino_t arg_inode, int arg_include_level, + const string& arg_name, bool arg_skipped = false, + bool arg_prefixes_checked = false) + : dev(arg_dev), inode(arg_inode), + include_level(arg_include_level), + name(arg_name), skipped(arg_skipped), + prefixes_checked(arg_prefixes_checked) { } }; diff --git a/src/scan.l b/src/scan.l index d41bcb601a..50f035fa2f 100644 --- a/src/scan.l +++ b/src/scan.l @@ -36,6 +36,13 @@ #include "plugin/Manager.h" +namespace { +struct ZeekINode { + dev_t dev; + ino_t ino; +}; +} + extern YYLTYPE yylloc; // holds start line and column of token extern EnumType* cur_enum_type; @@ -91,7 +98,7 @@ static string find_relative_script_file(const string& filename) return find_script_file(filename, bro_path()); } -static ino_t get_inode_num(FILE* f, const string& path) +static ZeekINode get_inode(FILE* f, const string& path) { struct stat b; @@ -99,20 +106,20 @@ static ino_t get_inode_num(FILE* f, const string& path) reporter->FatalError("fstat of %s failed: %s\n", path.c_str(), strerror(errno)); - return b.st_ino; + return {b.st_dev, b.st_ino}; } -static ino_t get_inode_num(const string& path) +static ZeekINode get_inode(const string& path) { FILE* f = open_file(path); if ( ! f ) reporter->FatalError("failed to open %s\n", path.c_str()); - ino_t inum = get_inode_num(f, path); + auto inode = get_inode(f, path); fclose(f); - return inum; + return inode; } class FileInfo { @@ -420,7 +427,8 @@ when return TOK_WHEN; else { // All we have to do is pretend we've already scanned it. - ScannedFile sf(get_inode_num(path), file_stack.length(), path, true); + auto i = get_inode(path); + ScannedFile sf(i.dev, i.ino, file_stack.length(), path, true); files_scanned.push_back(sf); } } @@ -587,13 +595,10 @@ YYLTYPE GetCurrentLocation() return currloc; } - -static bool already_scanned(ino_t i) +static bool already_scanned(ZeekINode in) { - list::const_iterator it; - - for ( it = files_scanned.begin(); it != files_scanned.end(); ++it ) - if ( it->inode == i ) + for ( const auto& it : files_scanned ) + if ( it.dev == in.dev && it.inode == in.ino ) return true; return false; @@ -601,7 +606,7 @@ static bool already_scanned(ino_t i) static bool already_scanned(const string& path) { - return already_scanned(get_inode_num(path)); + return already_scanned(get_inode(path)); } static int load_files(const char* orig_file) @@ -656,7 +661,7 @@ static int load_files(const char* orig_file) reporter->FatalError("can't open %s", file_path.c_str()); } - ino_t i = get_inode_num(f, file_path); + auto i = get_inode(f, file_path); if ( already_scanned(i) ) { @@ -666,7 +671,7 @@ static int load_files(const char* orig_file) return 0; } - ScannedFile sf(i, file_stack.length(), file_path); + ScannedFile sf(i.dev, i.ino, file_stack.length(), file_path); files_scanned.push_back(sf); if ( g_policy_debug && ! file_path.empty() )