#!/bin/env tclsh set file [dict get [info frame 0] file] source [file dirname $file]/pvrt.tcl proc fatal {num reason} { global argv0 puts stderr "fatal: $argv0: $reason" exit $num } if {[llength $argv] != 2} { puts stderr "usage: $argv0 FILE.PAC OUTDIR/" exit 1 } lassign $argv file dir set fp [open $file rb] binary scan [read $fp 0xc] {iii} magic numents startpos if {$magic != 0x00434150} { die 2 "${file}: unknown magic: [format %08x $magic]" } set hdrlen [expr {0xc + ($numents * 4)}] puts "${file}: header length: $hdrlen ($numents entries)" puts "${file}: record start: $startpos" set endhdr [read $fp [expr {$numents * 4}]] binary scan $endhdr "i$numents" endtab puts "${file}: record end table: $endtab" seek $fp $startpos file mkdir $dir set pos $startpos set i 0 foreach endpt $endtab { set id [format %04d $i] set filebase $dir/$id set length [expr {$endpt - $pos}] set data [read $fp $length] set type [string range $data 0 3] switch -- $type { NZIP { puts "${file}: record $id: Deflate Compressed" set data [string range $data 8 end] set decom [zlib inflate $data] set magic [string range $decom 0 3] if {$magic in {GBIX PVRT}} { set ext pvr puts "${file}: record $id (decompressed): Sega PowerVR Texture" } else { set ext bin binary scan $type i tynum puts "${file}: record $id (decompressed): Unknown (magic 0x[format %08x $tynum])" } set fp2 [open ${filebase}.${ext} wb] puts $fp2 $decom close $fp2 if {$ext == "pvr"} { pvrt2tga::convert ${filebase}.${ext} ${filebase}.tga exec -- convert ${filebase}.tga ${filebase}.png file delete ${filebase}.tga puts "${file}: record $id (decompressed): Converted to PNG" } } NJCM { puts "${file}: record $id: Ninja Chunk Model" set fp2 [open ${filebase}.njcm wb] puts $fp2 $data close $fp2 } NJTL { puts "${file}: record $id: Ninja Texture List" set fp2 [open ${filebase}.njtl wb] puts $fp2 $data close $fp2 } NMDM { puts "${file}: record $id: Ninja Motion" set fp2 [open ${filebase}.nmdm wb] puts $fp2 $data close $fp2 } default { binary scan $type i tynum puts "${file}: record $id: Unknown (magic 0x[format %08x $tynum])" set fp2 [open ${filebase}.rec wb] puts $fp2 $data close $fp2 } } set pos $endpt incr i }