feat: new feature gate `initenv` to disable env ocalls on demand
diff --git a/sgx_tstd/Cargo.toml b/sgx_tstd/Cargo.toml
index e87b504..aa1604b 100644
--- a/sgx_tstd/Cargo.toml
+++ b/sgx_tstd/Cargo.toml
@@ -30,11 +30,12 @@
 crate-type = ["rlib"]
 
 [features]
-default = ["stdio"]
+default = ["stdio", "initenv"]
 backtrace = ["stdio", "sgx_backtrace_sys", "sgx_demangle"]
 stdio = []
 net = []
 pipe = []
+initenv = []
 thread = ["sgx_trts/thread"]
 untrusted_fs = []
 untrusted_time = []
diff --git a/sgx_tstd/src/rt.rs b/sgx_tstd/src/rt.rs
index 867c74d..628150e 100644
--- a/sgx_tstd/src/rt.rs
+++ b/sgx_tstd/src/rt.rs
@@ -25,6 +25,7 @@
 pub use core::panicking::{panic_display, panic_fmt};
 
 use crate::enclave::Enclave;
+#[cfg(feature = "initenv")]
 use crate::ffi::CString;
 use crate::slice;
 use crate::str;
@@ -145,6 +146,7 @@
 static EXIT: Once = Once::new();
 
 #[no_mangle]
+#[allow(unused)]
 unsafe extern "C" fn global_init_ecall(
     eid: u64,
     path: *const u8,
@@ -164,26 +166,29 @@
             }
         }
 
-        let parse_vec = |ptr: *const u8, len: usize| -> Vec<CString> {
-            if !ptr.is_null() && len > 0 {
-                let buf = slice::from_raw_parts(ptr, len);
-                buf.split(|&c| c == 0)
-                    .filter_map(|bytes| {
-                        if !bytes.is_empty() {
-                            CString::new(bytes).ok()
-                        } else {
-                            None
-                        }
-                    })
-                    .collect()
-            } else {
-                Vec::new()
-            }
-        };
+        #[cfg(feature = "initenv")]
+        {
+            let parse_vec = |ptr: *const u8, len: usize| -> Vec<CString> {
+                if !ptr.is_null() && len > 0 {
+                    let buf = slice::from_raw_parts(ptr, len);
+                    buf.split(|&c| c == 0)
+                        .filter_map(|bytes| {
+                            if !bytes.is_empty() {
+                                CString::new(bytes).ok()
+                            } else {
+                                None
+                            }
+                        })
+                        .collect()
+                } else {
+                    Vec::new()
+                }
+            };
 
-        let env = parse_vec(env, env_len);
-        let args = parse_vec(args, args_len);
-        sys::init(env, args);
+            let env = parse_vec(env, env_len);
+            let args = parse_vec(args, args_len);
+            sys::init(env, args);
+        }
     });
 }
 
diff --git a/sgx_tstd/src/sys/mod.rs b/sgx_tstd/src/sys/mod.rs
index a517845..5dbb2e3 100644
--- a/sgx_tstd/src/sys/mod.rs
+++ b/sgx_tstd/src/sys/mod.rs
@@ -15,10 +15,13 @@
 // specific language governing permissions and limitations
 // under the License..
 
+#[cfg(feature = "initenv")]
 use crate::ffi::CString;
 use crate::io::ErrorKind;
 
-use sgx_oc::ocall::{self, OCallResult};
+#[cfg(feature = "initenv")]
+use sgx_oc::ocall;
+use sgx_oc::ocall::OCallResult;
 use sgx_oc as libc;
 use sgx_trts::error::abort;
 
@@ -59,6 +62,7 @@
 
 // SAFETY: must be called only once during runtime initialization.
 // NOTE: this is not guaranteed to run, for example when Rust code is called externally.
+#[cfg(feature = "initenv")]
 pub unsafe fn init(env: Vec<CString>, args: Vec<CString>) {
     let _ = ocall::initenv(Some(env));
     let _ = ocall::initargs(Some(args));