]> git.ipfire.org Git - thirdparty/suricata.git/commitdiff
rust: filecontainer API
authorVictor Julien <victor@inliniac.net>
Thu, 11 May 2017 14:58:55 +0000 (16:58 +0200)
committerVictor Julien <victor@inliniac.net>
Tue, 6 Jun 2017 07:20:56 +0000 (09:20 +0200)
Wrapper around Suricata's File and FileContainer API. Built around
assumption that a rust owned structure will have a
'SuricataFileContainer' member that is managed by the C-side of
things.

rust/src/core.rs
rust/src/filecontainer.rs [new file with mode: 0644]
rust/src/lib.rs
src/rust.h
src/suricata.c

index 8388da2733a6ed51b9dd153e38c3fdc36a6fd968..fb6edd26eb1b7c40d7d08e8e45c89f4f1b492dc0 100644 (file)
@@ -19,6 +19,8 @@
 
 extern crate libc;
 
+use filecontainer::*;
+
 /// Opaque C types.
 pub enum Flow {}
 pub enum DetectEngineState {}
@@ -55,6 +57,37 @@ pub type AppLayerDecoderEventsSetEventRawFunc =
 pub type AppLayerDecoderEventsFreeEventsFunc =
     extern "C" fn (events: *mut *mut AppLayerDecoderEvents);
 
+pub struct SuricataStreamingBufferConfig;
+
+//File *(*FileOpenFile)(FileContainer *, const StreamingBufferConfig *,
+//       const uint8_t *name, uint16_t name_len,
+//       const uint8_t *data, uint32_t data_len, uint16_t flags);
+pub type SCFileOpenFileWithId = extern "C" fn (
+        file_container: &FileContainer,
+        sbcfg: &SuricataStreamingBufferConfig,
+        track_id: u32,
+        name: *const u8, name_len: u16,
+        data: *const u8, data_len: u32,
+        flags: u16) -> File;
+//int (*FileCloseFile)(FileContainer *, const uint8_t *data, uint32_t data_len, uint16_t flags);
+pub type SCFileCloseFileById = extern "C" fn (
+        file_container: &FileContainer,
+        track_id: u32,
+        data: *const u8, data_len: u32,
+        flags: u16) -> i32;
+//int (*FileAppendData)(FileContainer *, const uint8_t *data, uint32_t data_len);
+pub type SCFileAppendDataById = extern "C" fn (
+        file_container: &FileContainer,
+        track_id: u32,
+        data: *const u8, data_len: u32) -> i32;
+// void FilePrune(FileContainer *ffc)
+pub type SCFilePrune = extern "C" fn (
+        file_container: &FileContainer);
+// void FileContainerRecycle(FileContainer *ffc)
+pub type SCFileContainerRecycle = extern "C" fn (
+        file_container: &FileContainer);
+
+
 // A Suricata context that is passed in from C. This is alternative to
 // using functions from Suricata directly, so they can be wrapped so
 // Rust unit tests will still compile when they are not linked
@@ -69,6 +102,18 @@ pub struct SuricataContext {
     DetectEngineStateFree: DetectEngineStateFreeFunc,
     AppLayerDecoderEventsSetEventRaw: AppLayerDecoderEventsSetEventRawFunc,
     AppLayerDecoderEventsFreeEvents: AppLayerDecoderEventsFreeEventsFunc,
+
+    pub FileOpenFile: SCFileOpenFileWithId,
+    pub FileCloseFile: SCFileCloseFileById,
+    pub FileAppendData: SCFileAppendDataById,
+    pub FileContainerRecycle: SCFileContainerRecycle,
+    pub FilePrune: SCFilePrune,
+}
+
+#[allow(non_snake_case)]
+#[repr(C)]
+pub struct SuricataFileContext {
+    pub files_sbcfg: &'static SuricataStreamingBufferConfig,
 }
 
 pub static mut SC: Option<&'static SuricataContext> = None;
diff --git a/rust/src/filecontainer.rs b/rust/src/filecontainer.rs
new file mode 100644 (file)
index 0000000..3d3c163
--- /dev/null
@@ -0,0 +1,118 @@
+/* Copyright (C) 2017 Open Information Security Foundation
+ *
+ * You can copy, redistribute or modify this Program under the terms of
+ * the GNU General Public License version 2 as published by the Free
+ * Software Foundation.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * version 2 along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+ * 02110-1301, USA.
+ */
+
+extern crate libc;
+use std::ptr;
+use libc::{c_void};
+
+use log::*;
+use core::*;
+
+pub struct File;
+#[repr(C)]
+#[derive(Debug)]
+pub struct FileContainer {
+    head: * mut c_void,
+    tail: * mut c_void,
+}
+
+impl FileContainer {
+    pub fn default() -> FileContainer {
+        FileContainer { head:ptr::null_mut(), tail:ptr::null_mut() }
+    }
+    pub fn free(&mut self) {
+        SCLogDebug!("freeing self");
+        match unsafe {SC} {
+            None => panic!("BUG no suricata_config"),
+            Some(c) => {
+                (c.FileContainerRecycle)(&self);
+            },
+        }
+    }
+
+    pub fn file_open(&mut self, cfg: &'static SuricataFileContext, track_id: &u32, name: &[u8], flags: u16) -> i32 {
+        match unsafe {SC} {
+            None => panic!("BUG no suricata_config"),
+            Some(c) => {
+                SCLogDebug!("FILE {:p} OPEN flags {:04X}", &self, flags);
+                //let ref res =
+
+                (c.FileOpenFile)(&self, cfg.files_sbcfg, *track_id,
+                        name.as_ptr(), name.len() as u16,
+                        ptr::null(), 0u32, flags);
+
+                //if !res {
+                //    panic!("c.fn_fileopenfile failed");
+                //}
+                0
+            }
+        }
+    }
+
+    pub fn file_append(&mut self, track_id: &u32, data: &[u8]) -> i32 {
+        SCLogDebug!("FILECONTAINER: append {}", data.len());
+        if data.len() == 0 {
+            return 0
+        }
+        match unsafe {SC} {
+            None => panic!("BUG no suricata_config"),
+            Some(c) => {
+                let res = (c.FileAppendData)(&self, *track_id,
+                        data.as_ptr(), data.len() as u32);
+                if res != 0 {
+                    panic!("c.fn_fileappenddata failed");
+                }
+                res
+            }
+        }
+    }
+
+    pub fn file_close(&mut self, track_id: &u32, flags: u16) -> i32 {
+        SCLogDebug!("FILECONTAINER: CLOSEing");
+
+        match unsafe {SC} {
+            None => panic!("BUG no suricata_config"),
+            Some(c) => {
+                let res = (c.FileCloseFile)(&self, *track_id, ptr::null(), 0u32, flags);
+                if res != 0 {
+                    panic!("c.fn_fileclosefile failed");
+                }
+                res
+            }
+        }
+
+    }
+
+    pub fn files_prune(&mut self) {
+        SCLogDebug!("FILECONTAINER: pruning");
+        match unsafe {SC} {
+            None => panic!("BUG no suricata_config"),
+            Some(c) => {
+                (c.FilePrune)(&self);
+            }
+        }
+    }
+
+    pub fn file_set_txid_on_last_file(&mut self, tx_id: u64) {
+        match unsafe {SC} {
+            None => panic!("BUG no suricata_config"),
+            Some(c) => {
+                (c.FileSetTx)(&self, tx_id);
+            }
+        }
+    }
+}
index aa214304d64f8b75de12b0a91d4ebc80a0c49a8c..a80c14b417a5d5fd46bfde74adbf7089fbd7607f 100644 (file)
@@ -15,6 +15,8 @@
  * 02110-1301, USA.
  */
 
+extern crate libc;
+
 #[macro_use]
 extern crate nom;
 
@@ -27,6 +29,7 @@ pub mod core;
 pub mod conf;
 pub mod json;
 pub mod applayer;
+pub mod filecontainer;
 
 #[cfg(feature = "lua")]
 pub mod lua;
index b5ee1b50383386f81518a68b64da8d738b833786..0dcf54f7a073ba1b20e7a1edbdb79ed690b6f294 100644 (file)
@@ -25,6 +25,17 @@ typedef struct SuricataContext_ {
     void (*AppLayerDecoderEventsSetEventRaw)(AppLayerDecoderEvents **,
             uint8_t);
     void (*AppLayerDecoderEventsFreeEvents)(AppLayerDecoderEvents **);
+
+    File *(*FileOpenFileWithId)(FileContainer *, const StreamingBufferConfig *,
+        uint32_t track_id, const uint8_t *name, uint16_t name_len,
+        const uint8_t *data, uint32_t data_len, uint16_t flags);
+    int (*FileCloseFileById)(FileContainer *, uint32_t track_id,
+            const uint8_t *data, uint32_t data_len, uint16_t flags);
+    int (*FileAppendDataById)(FileContainer *, uint32_t track_id,
+            const uint8_t *data, uint32_t data_len);
+    void (*FileContainerRecycle)(FileContainer *ffc);
+    void (*FilePrune)(FileContainer *ffc);
+
 } SuricataContext;
 
 #endif /* !__RUST_H__ */
index afda25d67ea6070c481a6d8e5d263da4859b1956..a5f76a40f80ce451f82e181c8906198764ef1d04 100644 (file)
@@ -2786,6 +2786,13 @@ int main(int argc, char **argv)
     context.AppLayerDecoderEventsSetEventRaw =
         AppLayerDecoderEventsSetEventRaw;
     context.AppLayerDecoderEventsFreeEvents = AppLayerDecoderEventsFreeEvents;
+
+    context.FileOpenFileWithId = FileOpenFileWithId;
+    context.FileCloseFileById = FileCloseFileById;
+    context.FileAppendDataById = FileAppendDataById;
+    context.FileContainerRecycle = FileContainerRecycle;
+    context.FilePrune = FilePrune;
+
     rs_init(&context);
 #endif