Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: provide interface frida.Device #29

Merged
merged 2 commits into from
Jan 25, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
37 changes: 34 additions & 3 deletions frida/device.go
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,38 @@ import (
"unsafe"
)

// Device represents FridaDevice struct from frida-core
type DeviceInt interface {
ID() string
Name() string
DeviceIcon() any
Bus() *Bus
Manager() *DeviceManager
IsLost() bool
Params() (map[string]any, error)
FrontmostApplication(scope Scope) (*Application, error)
EnumerateApplications(identifier string, scope Scope) ([]*Application, error)
ProcessByPID(pid int, scope Scope) (*Process, error)
ProcessByName(name string, scope Scope) (*Process, error)
FindProcessByPID(pid int, scope Scope) (*Process, error)
FindProcessByName(name string, scope Scope) (*Process, error)
EnumerateProcesses(scope Scope) ([]*Process, error)
EnableSpawnGating() error
DisableSpawnGating() error
EnumeratePendingSpawn() ([]*Spawn, error)
EnumeratePendingChildren() ([]*Child, error)
Spawn(name string, opts *SpawnOptions) (int, error)
Input(pid int, data []byte) error
Resume(pid int) error
Kill(pid int) error
Attach(val any, opts *SessionOptions) (*Session, error)
InjectLibraryFile(target any, path, entrypoint, data string) (uint, error)
InjectLibraryBlob(target any, byteData []byte, entrypoint, data string) (uint, error)
OpenChannel(address string) (*IOStream, error)
Clean()
On(sigName string, fn any)
}

// Device represents Device struct from frida-core
type Device struct {
device *C.FridaDevice
}
Expand Down Expand Up @@ -62,10 +93,10 @@ func (d *Device) Bus() *Bus {
}

// Manager returns device manager for the device.
func (d *Device) Manager() DeviceManager {
func (d *Device) Manager() *DeviceManager {
if d.device != nil {
mgr := C.frida_device_get_manager(d.device)
return &deviceManager{mgr}
return &DeviceManager{mgr}
}
return nil
}
Expand Down
10 changes: 5 additions & 5 deletions frida/frida.go
Original file line number Diff line number Diff line change
Expand Up @@ -34,14 +34,14 @@ func Version() string {
return C.GoString(C.frida_version_string())
}

func getDeviceManager() DeviceManager {
func getDeviceManager() *DeviceManager {
v, ok := data.Load("mgr")
if !ok {
mgr := NewDeviceManager()
data.Store("mgr", mgr)
return mgr
}
return v.(DeviceManager)
return v.(*DeviceManager)
}

// LocalDevice is a wrapper around DeviceByType(DeviceTypeLocal).
Expand All @@ -51,7 +51,7 @@ func LocalDevice() *Device {
if !ok {
dev, _ := mgr.DeviceByType(DeviceTypeLocal)
data.Store("localDevice", dev)
return dev
return dev.(*Device)
}
return v.(*Device)
}
Expand All @@ -71,7 +71,7 @@ func USBDevice() *Device {
return nil
}
data.Store("usbDevice", dev)
return dev
return dev.(*Device)
}
return v.(*Device)
}
Expand All @@ -91,7 +91,7 @@ func DeviceByID(id string) (*Device, error) {
return nil, err
}
data.Store(id, dev)
return dev, nil
return v.(*Device), nil
}
return v.(*Device), nil
}
Expand Down
62 changes: 31 additions & 31 deletions frida/manager.go
Original file line number Diff line number Diff line change
Expand Up @@ -5,39 +5,39 @@ import "C"

import "unsafe"

// DeviceManager is the device DeviceManager interface
type DeviceManager interface {
// DeviceManagerInt is the device DeviceManagerInt interface
type DeviceManagerInt interface {
Close() error
EnumerateDevices() ([]*Device, error)
LocalDevice() (*Device, error)
USBDevice() (*Device, error)
RemoteDevice() (*Device, error)
DeviceByID(id string) (*Device, error)
DeviceByType(devType DeviceType) (*Device, error)
FindDeviceByID(id string) (*Device, error)
FindDeviceByType(devType DeviceType) (*Device, error)
AddRemoteDevice(address string, remoteOpts *RemoteDeviceOptions) (*Device, error)
EnumerateDevices() ([]DeviceInt, error)
LocalDevice() (DeviceInt, error)
USBDevice() (DeviceInt, error)
RemoteDevice() (DeviceInt, error)
DeviceByID(id string) (DeviceInt, error)
DeviceByType(devType DeviceType) (DeviceInt, error)
FindDeviceByID(id string) (DeviceInt, error)
FindDeviceByType(devType DeviceType) (DeviceInt, error)
AddRemoteDevice(address string, remoteOpts *RemoteDeviceOptions) (DeviceInt, error)
RemoveRemoteDevice(address string) error
Clean()
On(sigName string, fn any)

getManager() *C.FridaDeviceManager
}

// deviceManager is the main structure which holds on devices available to Frida
// Single instance of the deviceManager is created when you call frida.Attach() or frida.LocalDevice().
type deviceManager struct {
// DeviceManager is the main structure which holds on devices available to Frida
// Single instance of the DeviceManager is created when you call frida.Attach() or frida.LocalDevice().
type DeviceManager struct {
manager *C.FridaDeviceManager
}

// NewDeviceManager returns new frida device manager.
func NewDeviceManager() DeviceManager {
func NewDeviceManager() *DeviceManager {
manager := C.frida_device_manager_new()
return &deviceManager{manager}
return &DeviceManager{manager}
}

// Close method will close current manager.
func (d *deviceManager) Close() error {
func (d *DeviceManager) Close() error {
var err *C.GError
C.frida_device_manager_close_sync(d.manager, nil, &err)
if err != nil {
Expand All @@ -47,15 +47,15 @@ func (d *deviceManager) Close() error {
}

// EnumerateDevices will return all connected devices.
func (d *deviceManager) EnumerateDevices() ([]*Device, error) {
func (d *DeviceManager) EnumerateDevices() ([]DeviceInt, error) {
var err *C.GError
deviceList := C.frida_device_manager_enumerate_devices_sync(d.manager, nil, &err)
if err != nil {
return nil, &FError{err}
}

numDevices := int(C.frida_device_list_size(deviceList))
devices := make([]*Device, numDevices)
devices := make([]DeviceInt, numDevices)

for i := 0; i < numDevices; i++ {
device := C.frida_device_list_get(deviceList, C.gint(i))
Expand All @@ -67,23 +67,23 @@ func (d *deviceManager) EnumerateDevices() ([]*Device, error) {
}

// LocalDevice returns the device with type DeviceTypeLocal.
func (d *deviceManager) LocalDevice() (*Device, error) {
func (d *DeviceManager) LocalDevice() (DeviceInt, error) {
return d.DeviceByType(DeviceTypeLocal)
}

// USBDevice returns the device with type DeviceTypeUsb.
func (d *deviceManager) USBDevice() (*Device, error) {
func (d *DeviceManager) USBDevice() (DeviceInt, error) {
return d.DeviceByType(DeviceTypeUsb)
}

// RemoteDevice returns the device with type DeviceTypeRemote.
func (d *deviceManager) RemoteDevice() (*Device, error) {
func (d *DeviceManager) RemoteDevice() (DeviceInt, error) {
return d.DeviceByType(DeviceTypeRemote)
}

// DeviceByID will return device with id passed or an error if it can't find any.
// Note: the caller must call EnumerateDevices() to get devices that are of type usb
func (d *deviceManager) DeviceByID(id string) (*Device, error) {
func (d *DeviceManager) DeviceByID(id string) (DeviceInt, error) {
idC := C.CString(id)
defer C.free(unsafe.Pointer(idC))

Expand All @@ -99,7 +99,7 @@ func (d *deviceManager) DeviceByID(id string) (*Device, error) {

// DeviceByType will return device or an error by device type specified.
// Note: the caller must call EnumerateDevices() to get devices that are of type usb
func (d *deviceManager) DeviceByType(devType DeviceType) (*Device, error) {
func (d *DeviceManager) DeviceByType(devType DeviceType) (DeviceInt, error) {
var err *C.GError
device := C.frida_device_manager_get_device_by_type_sync(d.manager,
C.FridaDeviceType(devType),
Expand All @@ -114,7 +114,7 @@ func (d *deviceManager) DeviceByType(devType DeviceType) (*Device, error) {

// FindDeviceByID will try to find the device by id specified
// Note: the caller must call EnumerateDevices() to get devices that are of type usb
func (d *deviceManager) FindDeviceByID(id string) (*Device, error) {
func (d *DeviceManager) FindDeviceByID(id string) (DeviceInt, error) {
devID := C.CString(id)
defer C.free(unsafe.Pointer(devID))

Expand All @@ -135,7 +135,7 @@ func (d *deviceManager) FindDeviceByID(id string) (*Device, error) {

// FindDeviceByType will try to find the device by device type specified
// Note: the caller must call EnumerateDevices() to get devices that are of type usb
func (d *deviceManager) FindDeviceByType(devType DeviceType) (*Device, error) {
func (d *DeviceManager) FindDeviceByType(devType DeviceType) (DeviceInt, error) {
timeout := C.gint(defaultDeviceTimeout)

var err *C.GError
Expand All @@ -152,7 +152,7 @@ func (d *deviceManager) FindDeviceByType(devType DeviceType) (*Device, error) {
}

// AddRemoteDevice add a remote device from the provided address with remoteOpts populated
func (d *deviceManager) AddRemoteDevice(address string, remoteOpts *RemoteDeviceOptions) (*Device, error) {
func (d *DeviceManager) AddRemoteDevice(address string, remoteOpts *RemoteDeviceOptions) (DeviceInt, error) {
addressC := C.CString(address)
defer C.free(unsafe.Pointer(addressC))

Expand All @@ -166,7 +166,7 @@ func (d *deviceManager) AddRemoteDevice(address string, remoteOpts *RemoteDevice
}

// RemoveRemoteDevice removes remote device available at address
func (d *deviceManager) RemoveRemoteDevice(address string) error {
func (d *DeviceManager) RemoveRemoteDevice(address string) error {
addressC := C.CString(address)
defer C.free(unsafe.Pointer(addressC))

Expand All @@ -182,7 +182,7 @@ func (d *deviceManager) RemoveRemoteDevice(address string) error {
}

// Clean will clean the resources held by the manager.
func (d *deviceManager) Clean() {
func (d *DeviceManager) Clean() {
clean(unsafe.Pointer(d.manager), unrefFrida)
}

Expand All @@ -193,10 +193,10 @@ func (d *deviceManager) Clean() {
// - "added" with callback as func(device *frida.Device) {}
// - "removed" with callback as func(device *frida.Device) {}
// - "changed" with callback as func() {}
func (d *deviceManager) On(sigName string, fn any) {
func (d *DeviceManager) On(sigName string, fn any) {
connectClosure(unsafe.Pointer(d.manager), sigName, fn)
}

func (d *deviceManager) getManager() *C.FridaDeviceManager {
func (d *DeviceManager) getManager() *C.FridaDeviceManager {
return d.manager
}
2 changes: 1 addition & 1 deletion frida/portal_service.go
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@ func NewPortal(clusterParams, controlParams *EndpointParameters) *Portal {
}

// Device returns portal device.
func (p *Portal) Device() *Device {
func (p *Portal) Device() DeviceInt {
dev := C.frida_portal_service_get_device(p.portal)
return &Device{dev}
}
Expand Down
Loading