Synology PAT/SPK ์ํธํ ์์นด์ด๋ธ ๋ณตํธํ
Tip
AWS ํดํน ๋ฐฐ์ฐ๊ธฐ ๋ฐ ์ฐ์ตํ๊ธฐ:
HackTricks Training AWS Red Team Expert (ARTE)
GCP ํดํน ๋ฐฐ์ฐ๊ธฐ ๋ฐ ์ฐ์ตํ๊ธฐ:HackTricks Training GCP Red Team Expert (GRTE)
Azure ํดํน ๋ฐฐ์ฐ๊ธฐ ๋ฐ ์ฐ์ตํ๊ธฐ:
HackTricks Training Azure Red Team Expert (AzRTE)
HackTricks ์ง์ํ๊ธฐ
- ๊ตฌ๋ ๊ณํ ํ์ธํ๊ธฐ!
- **๐ฌ ๋์ค์ฝ๋ ๊ทธ๋ฃน ๋๋ ํ ๋ ๊ทธ๋จ ๊ทธ๋ฃน์ ์ฐธ์ฌํ๊ฑฐ๋ ํธ์ํฐ ๐ฆ @hacktricks_live๋ฅผ ํ๋ก์ฐํ์ธ์.
- HackTricks ๋ฐ HackTricks Cloud ๊นํ๋ธ ๋ฆฌํฌ์งํ ๋ฆฌ์ PR์ ์ ์ถํ์ฌ ํดํน ํธ๋ฆญ์ ๊ณต์ ํ์ธ์.
๊ฐ์
์ฌ๋ฌ Synology ์ฅ์น (DSM/BSM NAS, BeeStation ๋ฑ)๋ ์ํธํ๋ PAT / SPK ์์นด์ด๋ธ๋ก ํ์จ์ด ๋ฐ ์ ํ๋ฆฌ์ผ์ด์ ํจํค์ง๋ฅผ ๋ฐฐํฌํฉ๋๋ค. ์ด๋ฌํ ์์นด์ด๋ธ๋ ๊ณต์ ์ถ์ถ ๋ผ์ด๋ธ๋ฌ๋ฆฌ์ ๋ด์ฅ๋ ํ๋์ฝ๋ฉ๋ ํค ๋๋ถ์ ๊ณต๊ฐ ๋ค์ด๋ก๋ ํ์ผ๋ง์ผ๋ก ์คํ๋ผ์ธ์์ ๋ณตํธํํ ์ ์์ต๋๋ค.
์ด ํ์ด์ง๋ ์ํธํ๋ ํ์์ด ์๋ํ๋ ๋ฐฉ์๊ณผ ๊ฐ ํจํค์ง ๋ด๋ถ์ ์๋ ํ๋ฌธ TAR๋ฅผ ์์ ํ ๋ณต๊ตฌํ๋ ๋ฐฉ๋ฒ์ ๋จ๊ณ๋ณ๋ก ๋ฌธ์ํํฉ๋๋ค. ์ด ์ ์ฐจ๋ Pwn2Own Ireland 2024 ๋์ ์ํ๋ Synacktiv ์ฐ๊ตฌ๋ฅผ ๊ธฐ๋ฐ์ผ๋ก ํ๋ฉฐ ์คํ ์์ค ๋๊ตฌ synodecrypt์์ ๊ตฌํ๋์์ต๋๋ค.
โ ๏ธ ํ์์
*.pat(์์คํ ์ ๋ฐ์ดํธ)์*.spk(์ ํ๋ฆฌ์ผ์ด์ ) ์์นด์ด๋ธ ๋ชจ๋์ ๋ํด ์ ํํ ๋์ผํฉ๋๋ค โ ์ ํ๋๋ ํ๋์ฝ๋ฉ๋ ํค ์๋ง ๋ค๋ฆ ๋๋ค.
1. ์์นด์ด๋ธ ๊ฐ์ ธ์ค๊ธฐ
ํ์จ์ด/์ ํ๋ฆฌ์ผ์ด์ ์ ๋ฐ์ดํธ๋ ์ผ๋ฐ์ ์ผ๋ก Synology์ ๊ณต๊ฐ ํฌํธ์์ ๋ค์ด๋ก๋ํ ์ ์์ต๋๋ค:
$ wget https://archive.synology.com/download/Os/BSM/BSM_BST150-4T_65374.pat
2. PAT ๊ตฌ์กฐ ๋คํํ๊ธฐ (์ ํ ์ฌํญ)
*.pat ์ด๋ฏธ์ง๋ ์ฌ๋ฌ ํ์ผ(๋ถํธ ๋ก๋, ์ปค๋, rootfs, ํจํค์ง ๋ฑ)์ ํฌํจํ๋ cpio ๋ฒ๋ค์
๋๋ค. ๋ฌด๋ฃ ์ ํธ๋ฆฌํฐ patology๋ ํด๋น ๋ํผ๋ฅผ ๊ฒ์ฌํ๋ ๋ฐ ์ ์ฉํฉ๋๋ค:
$ python3 patology.py --dump -i BSM_BST150-4T_65374.pat
[โฆ]
$ ls
DiskCompatibilityDB.tar hda1.tgz rd.bin packages/ โฆ
*.spk ํ์ผ์ ๊ฒฝ์ฐ 3๋จ๊ณ๋ก ๋ฐ๋ก ์ด๋ํ ์ ์์ต๋๋ค.
3. Synology ์ถ์ถ ๋ผ์ด๋ธ๋ฌ๋ฆฌ ์ถ์ถ
์ค์ ๋ณตํธํ ๋ก์ง์ ๋ค์์ ์์ต๋๋ค:
/usr/syno/sbin/synoarchiveโ ๋ฉ์ธ CLI ๋ํผ/usr/lib/libsynopkg.so.1โ DSM UI์์ ๋ํผ ํธ์ถlibsynocodesign.soโ ์ํธํ ๊ตฌํ ํฌํจ
๋ ๋ฐ์ด๋๋ฆฌ๋ ์์คํ
rootfs (hda1.tgz) ๋ฐ ์์ถ๋ init-rd (rd.bin)์ ์กด์ฌํฉ๋๋ค. PAT๋ง ์๋ ๊ฒฝ์ฐ ๋ค์๊ณผ ๊ฐ์ ๋ฐฉ๋ฒ์ผ๋ก ๊ฐ์ ธ์ฌ ์ ์์ต๋๋ค:
# rd.bin is LZMA-compressed CPIO
$ lzcat rd.bin | cpio -id 2>/dev/null
$ file usr/lib/libsynocodesign.so
usr/lib/libsynocodesign.so: ELF 64-bit LSB shared object, ARM aarch64, โฆ
4. ํ๋์ฝ๋ฉ๋ ํค ๋ณต๊ตฌํ๊ธฐ (get_keys)
libsynocodesign.so ๋ด๋ถ์ get_keys(int keytype) ํจ์๋ ์์ฒญ๋ ์์นด์ด๋ธ ํจ๋ฐ๋ฆฌ์ ๋ํด ๋ ๊ฐ์ 128๋นํธ ์ ์ญ ๋ณ์๋ฅผ ๋จ์ํ ๋ฐํํฉ๋๋ค:
case 0: // PAT (system)
case 10:
case 11:
signature_key = qword_23A40;
master_key = qword_23A68;
break;
case 3: // SPK (applications)
signature_key = qword_23AE0;
master_key = qword_23B08;
break;
- signature_key โ ์์นด์ด๋ธ ํค๋๋ฅผ ๊ฒ์ฆํ๋ ๋ฐ ์ฌ์ฉ๋๋ Ed25519 ๊ณต๊ฐ ํค.
- master_key โ ์์นด์ด๋ธ๋ณ ์ํธํ ํค๋ฅผ ํ์ํ๋ ๋ฐ ์ฌ์ฉ๋๋ ๋ฃจํธ ํค.
๊ฐ DSM ์ฃผ์ ๋ฒ์ ๋ง๋ค ์ด ๋ ์์๋ฅผ ํ ๋ฒ๋ง ๋คํํ๋ฉด ๋ฉ๋๋ค.
5. ํค๋ ๊ตฌ์กฐ ๋ฐ ์๋ช ๊ฒ์ฆ
synoarchive_open() โ support_format_synoarchive() โ archive_read_support_format_synoarchive()๋ ๋ค์์ ์ํํฉ๋๋ค:
- ๋งค์ง ์ฝ๊ธฐ (3 ๋ฐ์ดํธ)
0xBFBAAD๋๋0xADBEEF. - ๋ฆฌํ ์๋์ 32๋นํธ
header_len์ฝ๊ธฐ. header_len๋ฐ์ดํธ + ๋ค์ 0x40 ๋ฐ์ดํธ Ed25519 ์๋ช ์ฝ๊ธฐ.crypto_sign_verify_detached()๊ฐ ์ฑ๊ณตํ ๋๊น์ง ๋ชจ๋ ๋ด์ฅ ๊ณต๊ฐ ํค๋ฅผ ๋ฐ๋ณตํฉ๋๋ค.- MessagePack์ผ๋ก ํค๋๋ฅผ ๋์ฝ๋ฉํ์ฌ ๊ฒฐ๊ณผ๋ฅผ ์์ฑํฉ๋๋ค:
[
data: bytes,
entries: [ [size: int, sha256: bytes], โฆ ],
archive_description: bytes,
serial_number: [bytes],
not_valid_before: int
]
entries๋ libarchive๊ฐ ๊ฐ ํ์ผ์ ๋ณตํธํํ ๋ ๋ฌด๊ฒฐ์ฑ ๊ฒ์ฌ๋ฅผ ์ํํ ์ ์๋๋ก ํฉ๋๋ค.
6. ์์นด์ด๋ธ๋ณ ์๋ธ ํค ์ ๋
MessagePack ํค๋์ ํฌํจ๋ data ๋ธ๋กญ์์:
subkey_id= ์คํ์ 0x10์ ๋ฆฌํ ์๋์uint64ctx= ์คํ์ 0x18์ 7 ๋ฐ์ดํธ
32๋ฐ์ดํธ ์คํธ๋ฆผ ํค๋ libsodium์ ์ฌ์ฉํ์ฌ ์ป์ต๋๋ค:
crypto_kdf_derive_from_key(kdf_subkey, 32, subkey_id, ctx, master_key);
7. Synology์ ์ปค์คํ libarchive ๋ฐฑ์๋
Synology๋ ๋งค์ง์ด 0xADBEEF์ผ ๋ ๊ฐ์ง โtarโ ํ์์ ๋ฑ๋กํ๋ ํจ์น๋ libarchive๋ฅผ ๋ฒ๋ค๋ก ์ ๊ณตํฉ๋๋ค:
register_format(
"tar", spk_bid, spk_options,
spk_read_header, spk_read_data, spk_read_data_skip,
NULL, spk_cleanup, NULL, NULL);
spk_read_header()
- Read 0x200 bytes
- nonce = buf[0:0x18]
- cipher = buf[0x18:0x18+0x193]
- crypto_secretstream_xchacha20poly1305_init_pull(state, nonce, kdf_subkey)
- crypto_secretstream_xchacha20poly1305_pull(state, tar_hdr, โฆ, cipher, 0x193)
๋ณตํธํ๋ tar_hdr๋ ๊ณ ์ ์ ์ธ POSIX TAR ํค๋์
๋๋ค.
spk_read_data()
while (remaining > 0):
chunk_len = min(0x400000, remaining) + 0x11 # +tag
buf = archive_read_ahead(chunk_len)
crypto_secretstream_xchacha20poly1305_pull(state, out, โฆ, buf, chunk_len)
remaining -= chunk_len - 0x11
๊ฐ 0x18-byte nonce๋ ์ํธํ๋ ์ฒญํฌ ์์ ์ถ๊ฐ๋ฉ๋๋ค.
๋ชจ๋ ํญ๋ชฉ์ด ์ฒ๋ฆฌ๋๋ฉด libarchive๋ ํ์ค ๋๊ตฌ๋ก ์์ถ ํด์ ํ ์ ์๋ ์๋ฒฝํ๊ฒ ์ ํจํ .tar ํ์ผ์ ์์ฑํฉ๋๋ค.
8. synodecrypt๋ก ๋ชจ๋ ๊ฒ์ ๋ณตํธํํฉ๋๋ค.
$ python3 synodecrypt.py SynologyPhotos-rtd1619b-1.7.0-0794.spk
[+] found matching keys (SPK)
[+] header signature verified
[+] 104 entries
[+] archive successfully decrypted โ SynologyPhotos-rtd1619b-1.7.0-0794.tar
$ tar xf SynologyPhotos-rtd1619b-1.7.0-0794.tar
synodecrypt๋ PAT/SPK๋ฅผ ์๋์ผ๋ก ๊ฐ์งํ๊ณ , ์ฌ๋ฐ๋ฅธ ํค๋ฅผ ๋ก๋ํ๋ฉฐ, ์์ ์ค๋ช
๋ ์ ์ฒด ์ฒด์ธ์ ์ ์ฉํฉ๋๋ค.
9. ์ผ๋ฐ์ ์ธ ํจ์
signature_key์master_key๋ฅผ ๊ตํํ์ง ๋ง์ญ์์ค โ ์ด๋ค์ ์๋ก ๋ค๋ฅธ ๋ชฉ์ ์ ๊ฐ์ง๊ณ ์์ต๋๋ค.- nonce๋ ๋ชจ๋ ๋ธ๋ก(ํค๋ ๋ฐ ๋ฐ์ดํฐ)์ ์ํธ๋ฌธ ์์ ์์นํฉ๋๋ค.
- ์ต๋ ์ํธํ ์ฒญํฌ ํฌ๊ธฐ๋ 0x400000 + 0x11(libsodium ํ๊ทธ)์ ๋๋ค.
- ํ DSM ์ธ๋์ ๋ํด ์์ฑ๋ ์์นด์ด๋ธ๋ ๋ค์ ๋ฆด๋ฆฌ์ค์์ ๋ค๋ฅธ ํ๋์ฝ๋ฉ๋ ํค๋ก ์ ํ๋ ์ ์์ต๋๋ค.
10. ์ถ๊ฐ ๋๊ตฌ
patologyโ PAT ์์นด์ด๋ธ๋ฅผ ํ์ฑ/๋คํํฉ๋๋ค.synodecryptโ PAT/SPK/๊ธฐํ๋ฅผ ๋ณตํธํํฉ๋๋ค.libsodiumโ XChaCha20-Poly1305 secretstream์ ์ฐธ์กฐ ๊ตฌํ์ ๋๋ค.msgpackโ ํค๋ ์ง๋ ฌํ.
์ฐธ๊ณ ๋ฌธํ
- Extraction of Synology encrypted archives โ Synacktiv (Pwn2Own IE 2024)
- synodecrypt on GitHub
- patology on GitHub
Tip
AWS ํดํน ๋ฐฐ์ฐ๊ธฐ ๋ฐ ์ฐ์ตํ๊ธฐ:
HackTricks Training AWS Red Team Expert (ARTE)
GCP ํดํน ๋ฐฐ์ฐ๊ธฐ ๋ฐ ์ฐ์ตํ๊ธฐ:HackTricks Training GCP Red Team Expert (GRTE)
Azure ํดํน ๋ฐฐ์ฐ๊ธฐ ๋ฐ ์ฐ์ตํ๊ธฐ:
HackTricks Training Azure Red Team Expert (AzRTE)
HackTricks ์ง์ํ๊ธฐ
- ๊ตฌ๋ ๊ณํ ํ์ธํ๊ธฐ!
- **๐ฌ ๋์ค์ฝ๋ ๊ทธ๋ฃน ๋๋ ํ ๋ ๊ทธ๋จ ๊ทธ๋ฃน์ ์ฐธ์ฌํ๊ฑฐ๋ ํธ์ํฐ ๐ฆ @hacktricks_live๋ฅผ ํ๋ก์ฐํ์ธ์.
- HackTricks ๋ฐ HackTricks Cloud ๊นํ๋ธ ๋ฆฌํฌ์งํ ๋ฆฌ์ PR์ ์ ์ถํ์ฌ ํดํน ํธ๋ฆญ์ ๊ณต์ ํ์ธ์.


