---
title: Shell Script Compiler (shc) 無法保護你的腳本
description: 簡述 shc 的弱點,希望大家能意識到 shc 充滿風險
tags: notes, shell, script, bash, linux
---
# Shell Script Compiler (shc) 無法保護你的腳本
>時至今日,仍有人誤會,使用 [shc](https://github.com/neurobin/shc) 將 Shell script 「編譯」成 binary 執行檔,就能保護腳本內容不被讀取。然而 shc 並不是真正的 compiler,它只是將腳本進行編碼和加密(encode and encrypt),並在執行時解密,將原始內容傳遞給 sh 或 bash 執行。換句話說 shc 僅是增加解析腳本的難度,卻無法真正防止腳本內容被解密。
>
> 本文URL: https://hackmd.io/@kmo/shc_not_safe
[TOC]
::: info
### :memo: 測試環境
- 作業系統: Rocky Linux 8 / Ubuntu 22.04
- shc 版本: 4.0.3
(本文應適用所有預設 bash 的 Linux 環境)
:::
::: danger
### :x: 危險行為
- 撰寫了一個 shell script,裡面包含 API 金鑰等機敏資訊
- 為了避免一般用戶讀到腳本內的 API 金鑰等機敏內容,所以使用 shc 轉成 binary 執行檔,看似一般人讀不到腳本內容,就放在 production 環境
:::
## 什麼是 Shell Script Compiler(shc) ?
- 原作者: [Francisco Rosales](http://www.datsi.fi.upm.es/~frosal/)
- 目前專案 URL: https://github.com/neurobin/shc
- 功能概述: Shell script -> 轉成 C 程式碼(進行編碼和加密) -> 編譯成 binary 執行檔
## shc 操作範例
- 範例腳本 `echo_love.sh` 內容
```bash=
#!/bin/bash
echo love
```
- 使用 shc 轉換成 binary 執行檔
```bash=
shc -f echo_love.sh -o echo_love
```
- 執行完會產生 2 個檔案
- `echo_love.sh.x.c`: C語言程式碼
- `echo_love`: binary 執行檔
- 此時執行 `./echo_love` 結果,會和 `./echo_love.sh` 一樣
## 檢查 binary 執行檔
此時透過 `file` 指令,檢查 binary 執行檔 `echo_love`,輸出結果看似和一般 binary 執行檔無異
```bash=
$ file echo_love
echo_love: ELF 64-bit LSB pie executable, x86-64, version 1 (SYSV), dynamically linked, interpreter /lib64/ld-linux-x86-64.so.2, BuildID[sha1]=f8078faffb5367415e42abe53529754804c72dae, for GNU/Linux 3.2.0, stripped
```

或是透過指令 `less` 去查看 binary 檔案內容,也會是一堆亂碼


## 如何繞過 shc 保護?
- 啟用 bash 環境變數`SHELLOPTS`,指定 `verbose`,接著執行 `echo_love` 即可看到腳本內容 print 出來
```bash=
env SHELLOPTS=verbose ./echo_love
```
- 輸出結果 (中間雖然大量空白或是排版不整齊,但腳本內容依然顯示出來)
```bash=
exec './echo_love' "$@"
#!/bin/bash
echo love
love
```
- 由於 [SHELLOPTS](https://www.gnu.org/software/bash/manual/html_node/Bash-Variables.html#index-SHELLOPTS) 是 readonly 變數,即使在腳本裡面嘗試添加`unset SHELLOPTS`去反制,也無法阻擋`SHELLOPTS=verbose`效果


## 後記
- 畢竟還是在 Shell 層執行,透過 Linux 系統其他機制,還是有機會看到 Shell script 內的行為。個人認為若有機敏內容,選擇用 Shell script 撰寫是非常不適合
- 機敏內容的程式碼,推薦使用其他程式語言改寫。得益於現今 AI 發展,我想應該不會花太多時間改寫
## 參考資料
- 法國 Linux 系統專家 Stéphane Chazelas 在網路上留言,才因此得知`SHELLOPTS`可以輕易 bypass shc 保護
https://unix.stackexchange.com/questions/64762/how-to-convert-a-shell-script-into-a-binary-executable/64765#comment92934_64765
---
{%hackmd @kmo/widget_license %}