Skip to content

Commit

Permalink
fix: swift protocol typeref ptr == 0 bind parsing
Browse files Browse the repository at this point in the history
  • Loading branch information
blacktop committed Apr 23, 2024
1 parent c26f9a4 commit bbd64de
Showing 1 changed file with 66 additions and 28 deletions.
94 changes: 66 additions & 28 deletions swift.go
Original file line number Diff line number Diff line change
Expand Up @@ -1112,17 +1112,27 @@ func (f *File) parseProtocol(r io.ReadSeeker, typ *swift.Type) (prot *swift.Prot
if err != nil {
return nil, fmt.Errorf("failed to read signature requirement protocol pointer: %v", err)
}
prot.SignatureRequirements[idx].Kind, err = f.GetBindName(ptr)
if err != nil {
f.cr.SeekToAddr(ptr)
pc, err := f.getContextDesc(ptr)
if err != nil {
return nil, fmt.Errorf("failed to read signature requirement protocol: %v", err)
if ptr == 0 {
ptr = req.TypeOrProtocolOrConformanceOrLayoutOff.GetRelPtrAddress()
if (ptr & 1) == 1 {
ptr = ptr &^ 1
}
if pc.Parent != "" {
prot.SignatureRequirements[idx].Kind = fmt.Sprintf("%s.%s", pc.Parent, pc.Name)
} else {
prot.SignatureRequirements[idx].Kind = pc.Name
if bind, err := f.GetBindName(ptr); err == nil {
prot.SignatureRequirements[idx].Kind = bind
}
} else {
prot.SignatureRequirements[idx].Kind, err = f.GetBindName(ptr)
if err != nil {
f.cr.SeekToAddr(ptr)
pc, err := f.getContextDesc(ptr)
if err != nil {
return nil, fmt.Errorf("failed to read signature requirement protocol: %v", err)
}
if pc.Parent != "" {
prot.SignatureRequirements[idx].Kind = fmt.Sprintf("%s.%s", pc.Parent, pc.Name)
} else {
prot.SignatureRequirements[idx].Kind = pc.Name
}
}
}
}
Expand Down Expand Up @@ -1262,25 +1272,37 @@ func (f *File) readProtocolConformance(r io.ReadSeeker, addr uint64) (pcd *swift
return nil, fmt.Errorf("failed to get indirect type descriptor pointer: %v", err)
}
ptr = f.vma.Convert(ptr)
if bind, err := f.GetBindName(ptr); err == nil {
pcd.TypeRef = &swift.Type{
Address: ptr,
Name: bind,
}
} else {
f.cr.SeekToAddr(ptr)
ctx, err := f.getContextDesc(ptr)
if err != nil {
return nil, fmt.Errorf("failed to get parent: %v", err)
if ptr == 0 {
if (addr & 1) == 1 {
addr = addr &^ 1
}
pcd.TypeRef = &swift.Type{
Address: ptr,
Name: ctx.Name,
Parent: &swift.Type{
Name: ctx.Parent,
},
if bind, err := f.GetBindName(addr); err == nil {
pcd.TypeRef = &swift.Type{
Address: addr,
Name: bind,
}
}
} else {
if bind, err := f.GetBindName(ptr); err == nil {
pcd.TypeRef = &swift.Type{
Address: ptr,
Name: bind,
}
} else {
f.cr.SeekToAddr(ptr)
ctx, err := f.getContextDesc(ptr)
if err != nil {
return nil, fmt.Errorf("failed to get parent: %v", err)
}
pcd.TypeRef = &swift.Type{
Address: ptr,
Name: ctx.Name,
Parent: &swift.Type{
Name: ctx.Parent,
},
}

}
}
case swift.DirectObjCClassName:
name, err := f.GetCString(pcd.TypeRefOffsest.GetRelPtrAddress())
Expand Down Expand Up @@ -1345,7 +1367,15 @@ func (f *File) readProtocolConformance(r io.ReadSeeker, addr uint64) (pcd *swift
return nil, fmt.Errorf("failed to read conditional requirement protocol pointer: %v", err)
}
ptr = f.vma.Convert(ptr)
if bind, err := f.GetBindName(ptr); err == nil {
if ptr == 0 {
ptr = req.TypeOrProtocolOrConformanceOrLayoutOff.GetRelPtrAddress()
if (ptr & 1) == 1 {
ptr = ptr &^ 1
}
if bind, err := f.GetBindName(ptr); err == nil {
pcd.ConditionalRequirements[idx].Kind = bind
}
} else if bind, err := f.GetBindName(ptr); err == nil {
pcd.ConditionalRequirements[idx].Kind = bind
} else {
f.cr.SeekToAddr(ptr)
Expand Down Expand Up @@ -2220,7 +2250,15 @@ func (f *File) parseGenericContext(ctx *swift.TypeGenericContext) (err error) {
return fmt.Errorf("failed to read generic requirement param protocol pointer: %v", err)
}
ptr = f.vma.Convert(ptr)
if bind, err := f.GetBindName(ptr); err == nil {
if ptr == 0 {
ptr = req.TypeOrProtocolOrConformanceOrLayoutOff.GetRelPtrAddress()
if (ptr & 1) == 1 {
ptr = ptr &^ 1
}
if bind, err := f.GetBindName(ptr); err == nil {
ctx.Requirements[idx].Kind = bind
}
} else if bind, err := f.GetBindName(ptr); err == nil {
ctx.Requirements[idx].Kind = bind
} else {
f.cr.SeekToAddr(ptr)
Expand Down

0 comments on commit bbd64de

Please sign in to comment.