Beispiel #1
0
func hasDynTag(f *elf.File, tag elf.DynTag) bool {
	ds := f.SectionByType(elf.SHT_DYNAMIC)
	if ds == nil {
		return false
	}
	d, err := ds.Data()
	if err != nil {
		return false
	}
	for len(d) > 0 {
		var t elf.DynTag
		switch f.Class {
		case elf.ELFCLASS32:
			t = elf.DynTag(f.ByteOrder.Uint32(d[0:4]))
			d = d[8:]
		case elf.ELFCLASS64:
			t = elf.DynTag(f.ByteOrder.Uint64(d[0:8]))
			d = d[16:]
		}
		if t == tag {
			return true
		}
	}
	return false
}
Beispiel #2
0
func hasDynTag(t *testing.T, f *elf.File, tag elf.DynTag) bool {
	ds := f.SectionByType(elf.SHT_DYNAMIC)
	if ds == nil {
		t.Error("no SHT_DYNAMIC section")
		return false
	}
	d, err := ds.Data()
	if err != nil {
		t.Errorf("can't read SHT_DYNAMIC contents: %v", err)
		return false
	}
	for len(d) > 0 {
		var t elf.DynTag
		switch f.Class {
		case elf.ELFCLASS32:
			t = elf.DynTag(f.ByteOrder.Uint32(d[:4]))
			d = d[8:]
		case elf.ELFCLASS64:
			t = elf.DynTag(f.ByteOrder.Uint64(d[:8]))
			d = d[16:]
		}
		if t == tag {
			return true
		}
	}
	return false
}
Beispiel #3
0
func Soname(data []byte) (so string, ok bool) {
	e, err := elf.NewFile(bytes.NewReader(data))
	if err != nil {
		return so, false
	}
	section := e.Section(".dynamic")
	if section == nil {
		// not a dynamic binary.
		return so, false
	}
	// e.stringtable(section.Link)
	dynstr, _ := e.Sections[section.Link].Data()

	switch e.Class {
	case elf.ELFCLASS64:
		n := section.Size / 16 // 2*sizeof(uintptr)
		values := make([]elf.Dyn64, n)
		binary.Read(section.Open(), binary.LittleEndian, values)
		for _, v := range values {
			if elf.DynTag(v.Tag) == elf.DT_SONAME {
				return getstring(dynstr, int(v.Val)), true
			}
		}
	case elf.ELFCLASS32:
		n := section.Size / 8
		values := make([]elf.Dyn32, n)
		binary.Read(section.Open(), binary.LittleEndian, values)
		for _, v := range values {
			if elf.DynTag(v.Tag) == elf.DT_SONAME {
				return getstring(dynstr, int(v.Val)), true
			}
		}
	}
	return "", false
}
Beispiel #4
0
func haveDynTag(file *elf.File, tag elf.DynTag) bool {

	if section := file.Section(".dynamic"); section != nil {

		reader := io.NewSectionReader(section, 0, int64(section.Size))
		switch file.Machine {

		case elf.EM_X86_64:
			for {
				var entry elf.Dyn64
				if err := binary.Read(reader, binary.LittleEndian, &entry); err != io.EOF {
					if elf.DynTag(entry.Tag) == tag {
						return true
					}
				} else {
					break
				}
			}

		case elf.EM_386:
			for {
				var entry elf.Dyn32
				if err := binary.Read(reader, binary.LittleEndian, &entry); err != io.EOF {
					if elf.DynTag(entry.Tag) == tag {
						return true
					}
				} else {
					break
				}
			}
		}
	}
	return false
}
Beispiel #5
0
func Depends(data []byte) (needed []string, err error) {
	e, err := elf.NewFile(bytes.NewReader(data))
	if err != nil {
		return nil, err
	}
	section := e.Section(".dynamic")
	if section == nil {
		// not a dynamic binary.
		return nil, nil
	}
	// e.stringtable(section.Link)
	dynstr, _ := e.Sections[section.Link].Data()

	switch e.Class {
	case elf.ELFCLASS64:
		n := section.Size / 16 // 2*sizeof(uintptr)
		values := make([]elf.Dyn64, n)
		binary.Read(section.Open(), binary.LittleEndian, values)
		for _, v := range values {
			if elf.DynTag(v.Tag) == elf.DT_NEEDED {
				so := getstring(dynstr, int(v.Val))
				needed = append(needed, so)
			}
		}
	case elf.ELFCLASS32:
		n := section.Size / 8
		values := make([]elf.Dyn32, n)
		binary.Read(section.Open(), binary.LittleEndian, values)
		for _, v := range values {
			if elf.DynTag(v.Tag) == elf.DT_NEEDED {
				so := getstring(dynstr, int(v.Val))
				needed = append(needed, so)
			}
		}
	}
	return needed, nil
}