Skip to content

Commit d4273cc

Browse files
author
dafenghuang
committed
feat: support parse png icon from pe file
1 parent ed7fd35 commit d4273cc

2 files changed

Lines changed: 76 additions & 0 deletions

File tree

icon.go

Lines changed: 46 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,46 @@
1+
package pe
2+
3+
import (
4+
"bytes"
5+
"errors"
6+
"image/png"
7+
)
8+
9+
func (pe *File) ParsePngIcon() ([]byte, error) {
10+
var iconEntry *ResourceDirectoryEntry
11+
for _, e := range pe.Resources.Entries {
12+
if e.ID != RTIcon {
13+
continue
14+
}
15+
if len(e.Directory.Entries) == 0 {
16+
return nil, errors.New("no entries found in resource directory")
17+
}
18+
iconEntry = &e
19+
break
20+
}
21+
if iconEntry == nil {
22+
return nil, errors.New("no icon found in resource directory")
23+
}
24+
25+
for _, iconItem := range iconEntry.Directory.Entries {
26+
if len(iconItem.Directory.Entries) == 0 {
27+
continue
28+
}
29+
30+
iconData := &iconItem.Directory.Entries[0]
31+
32+
offset, size := pe.GetOffsetFromRva(iconData.Data.Struct.OffsetToData), iconData.Data.Struct.Size
33+
34+
b, err := pe.ReadBytesAtOffset(offset, size)
35+
if err != nil {
36+
return nil, err
37+
}
38+
39+
_, err = png.Decode(bytes.NewBuffer(b))
40+
if err != nil {
41+
continue
42+
}
43+
return b, nil
44+
}
45+
return nil, errors.New("no valid png icon found")
46+
}

icon_test.go

Lines changed: 30 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,30 @@
1+
package pe
2+
3+
import (
4+
"os"
5+
"testing"
6+
)
7+
8+
func Test_ParseIcon(t *testing.T) {
9+
file, err := New("/Users/dafenghuang/Downloads/WeChatSetup.exe", &Options{})
10+
if err != nil {
11+
t.Errorf("open file failed, err %v", err)
12+
return
13+
}
14+
15+
err = file.Parse()
16+
if err != nil {
17+
t.Errorf("parse file failed, err %v", err)
18+
return
19+
}
20+
21+
iconBytes, err := file.ParsePngIcon()
22+
if err != nil {
23+
t.Errorf("parse icon failed, err %v", err)
24+
return
25+
}
26+
27+
os.WriteFile("test.png", iconBytes, 0644)
28+
29+
t.Logf("length %d", len(iconBytes))
30+
}

0 commit comments

Comments
 (0)