@@ -287,6 +287,118 @@ import (
287287 fmt.Printf (" Is monkey: %v \n " , monkey)
288288```
289289
290+ ### Toggle Flashlight
291+
292+ ``` go
293+ import (
294+ " github.com/AndroidGoLab/binder/android/hardware"
295+ " github.com/AndroidGoLab/binder/servicemanager"
296+ )
297+
298+ svc , err := sm.GetService (ctx, servicemanager.ServiceName (" media.camera" ))
299+ if err != nil {
300+ log.Fatal (err)
301+ }
302+ camera := hardware.NewCameraServiceProxy (svc)
303+
304+ // Turn torch on for camera "0"
305+ if err := camera.SetTorchMode (ctx, " 0" , true , nil ); err != nil {
306+ log.Fatal (err)
307+ }
308+ fmt.Println (" Torch ON" )
309+
310+ // Turn torch off
311+ _ = camera.SetTorchMode (ctx, " 0" , false , nil )
312+ ```
313+
314+ ### List All Installed Packages
315+
316+ ``` go
317+ import (
318+ " github.com/AndroidGoLab/binder/android/content/pm"
319+ " github.com/AndroidGoLab/binder/servicemanager"
320+ )
321+
322+ svc , err := sm.GetService (ctx, servicemanager.ServiceName (" package" ))
323+ if err != nil {
324+ log.Fatal (err)
325+ }
326+ pkgMgr := pm.NewPackageManagerProxy (svc)
327+
328+ packages , err := pkgMgr.GetAllPackages (ctx)
329+ if err != nil {
330+ log.Fatal (err)
331+ }
332+
333+ fmt.Printf (" Found %d packages:\n " , len (packages))
334+ for _ , pkg := range packages {
335+ fmt.Println (" " , pkg)
336+ }
337+ ```
338+
339+ ### Handle Errors Gracefully
340+
341+ ``` go
342+ import (
343+ " errors"
344+ aidlerrors " github.com/AndroidGoLab/binder/errors"
345+ " github.com/AndroidGoLab/binder/servicemanager"
346+ )
347+
348+ // Non-blocking service check (returns nil if not found)
349+ svc , err := sm.CheckService (ctx, servicemanager.ServiceName (" media.camera" ))
350+ if err != nil {
351+ log.Fatal (err)
352+ }
353+ if svc == nil {
354+ fmt.Println (" Camera service not available" )
355+ return
356+ }
357+
358+ // Typed error inspection
359+ _, err = someProxy.SomeMethod (ctx)
360+ var status *aidlerrors.StatusError
361+ if errors.As (err, &status) {
362+ switch status.Exception {
363+ case aidlerrors.ExceptionSecurity :
364+ fmt.Printf (" Permission denied: %s \n " , status.Message )
365+ case aidlerrors.ExceptionServiceSpecific :
366+ fmt.Printf (" Service error %d : %s \n " , status.ServiceSpecificCode , status.Message )
367+ default :
368+ fmt.Printf (" AIDL error: %v \n " , status)
369+ }
370+ }
371+ ```
372+
373+ ### Register a Server-Side Service
374+
375+ ``` go
376+ import (
377+ " github.com/AndroidGoLab/binder/binder"
378+ " github.com/AndroidGoLab/binder/parcel"
379+ " github.com/AndroidGoLab/binder/servicemanager"
380+ )
381+
382+ // Implement the TransactionReceiver interface
383+ type myService struct {}
384+
385+ func (s *myService ) Descriptor () string { return " com.example.IPingService" }
386+
387+ func (s *myService ) OnTransaction (
388+ ctx context.Context,
389+ code binder.TransactionCode,
390+ data *parcel.Parcel,
391+ ) (*parcel.Parcel, error) {
392+ reply := parcel.New ()
393+ binder.WriteStatus (reply, nil )
394+ reply.WriteString16 (" pong" )
395+ return reply, nil
396+ }
397+
398+ // Register with ServiceManager
399+ err := sm.AddService (ctx, servicemanager.ServiceName (" my.service" ), &myService{}, false , 0 )
400+ ```
401+
290402More examples: [ ` examples/ ` ] ( examples/ )
291403
292404<!-- END GENERATED USAGE_EXAMPLES -->
@@ -303,13 +415,17 @@ More examples: [`examples/`](examples/)
303415| [ ` camera_fwk ` ] ( examples/camera_fwk/ ) | |
304416| [ ` device_info ` ] ( examples/device_info/ ) | Device properties, build info |
305417| [ ` display_info ` ] ( examples/display_info/ ) | Display IDs, brightness, night mode |
418+ | [ ` error_handling ` ] ( examples/error_handling/ ) | Graceful error handling: service checks, typed errors, permissions |
419+ | [ ` flashlight_torch ` ] ( examples/flashlight_torch/ ) | Toggle flashlight/torch via ICameraService |
306420| [ ` getservice_vs_checkservice ` ] ( examples/getservice_vs_checkservice/ ) | Binary getservice_vs_checkservice compares GetService vs CheckService |
307421| [ ` gps_location ` ] ( examples/gps_location/ ) | Live GPS fix via ILocationListener callback |
308422| [ ` keymint_delete_test ` ] ( examples/keymint_delete_test/ ) | Binary keymint_delete_test calls DeleteAllKeys on the KeyMint HAL |
423+ | [ ` list_packages ` ] ( examples/list_packages/ ) | List all installed packages via GetAllPackages |
309424| [ ` list_services ` ] ( examples/list_services/ ) | Enumerate all binder services, ping each |
310425| [ ` package_query ` ] ( examples/package_query/ ) | Package list, installation info |
311426| [ ` power_status ` ] ( examples/power_status/ ) | Power supply state, charging info |
312427| [ ` security_test_apk ` ] ( examples/security_test_apk/ ) | Binary security_test_apk probes whether an app-sandboxed process can |
428+ | [ ` server_service ` ] ( examples/server_service/ ) | Register a Go service and call it back via binder |
313429| [ ` softap_manage ` ] ( examples/softap_manage/ ) | WiFi hotspot enable/disable, config |
314430| [ ` softap_tether_offload ` ] ( examples/softap_tether_offload/ ) | Tethering offload config, stats |
315431| [ ` softap_wifi_hal ` ] ( examples/softap_wifi_hal/ ) | WiFi chip info, AP interface state |
@@ -1833,6 +1949,88 @@ go run ./cmd/binder-mcp/ --mode remote
18331949
18341950<!-- END GENERATED BINDER_MCP -->
18351951
1952+ ## Using binder-mcp with AI Agents
1953+
1954+ <!-- BEGIN GENERATED AGENT_CONFIGS -->
1955+
1956+ ### Installation
1957+
1958+ ``` bash
1959+ # Via go install
1960+ go install github.com/AndroidGoLab/binder/cmd/binder-mcp@latest
1961+
1962+ # Via GitHub releases (pre-built binaries)
1963+ # Download from https://github.com/AndroidGoLab/binder/releases
1964+
1965+ # Via Docker (host mode)
1966+ docker run ghcr.io/androidgolab/binder-mcp
1967+ ```
1968+
1969+ ### Claude Code
1970+
1971+ ``` bash
1972+ claude mcp add --transport stdio binder-mcp -- binder-mcp --mode remote
1973+ ```
1974+
1975+ ### Cursor
1976+
1977+ Add to ` .cursor/mcp.json ` :
1978+
1979+ ``` json
1980+ {
1981+ "mcpServers" : {
1982+ "binder-mcp" : {
1983+ "command" : " binder-mcp" ,
1984+ "args" : [" --mode" , " remote" ]
1985+ }
1986+ }
1987+ }
1988+ ```
1989+
1990+ ### Windsurf
1991+
1992+ Add to ` ~/.codeium/windsurf/mcp_config.json ` :
1993+
1994+ ``` json
1995+ {
1996+ "mcpServers" : {
1997+ "binder-mcp" : {
1998+ "command" : " binder-mcp" ,
1999+ "args" : [" --mode" , " remote" ]
2000+ }
2001+ }
2002+ }
2003+ ```
2004+
2005+ ### Cline
2006+
2007+ Add to Cline MCP settings:
2008+
2009+ ``` json
2010+ {
2011+ "mcpServers" : {
2012+ "binder-mcp" : {
2013+ "command" : " binder-mcp" ,
2014+ "args" : [" --mode" , " remote" ],
2015+ "alwaysAllow" : [" list_services" , " get_device_info" , " take_screenshot" ]
2016+ }
2017+ }
2018+ }
2019+ ```
2020+
2021+ ### On-device mode (via adb)
2022+
2023+ ``` bash
2024+ # Build for Android
2025+ GOOS=linux GOARCH=arm64 CGO_ENABLED=0 go build -o binder-mcp ./cmd/binder-mcp/
2026+ adb push binder-mcp /data/local/tmp/
2027+
2028+ # Configure agent to use adb transport
2029+ claude mcp add --transport stdio binder-mcp -- adb shell /data/local/tmp/binder-mcp
2030+ ```
2031+
2032+ <!-- END GENERATED AGENT_CONFIGS -->
2033+
18362034## Interoperability
18372035
18382036<!-- BEGIN GENERATED INTEROPERABILITY -->
@@ -1924,6 +2122,6 @@ See the example app at [`examples/gomobile/`](examples/gomobile/).
19242122│ ├── hardware/ HAL interfaces
19252123│ └── ... 399 packages total
19262124├── com/ AOSP com.android.* service proxies
1927- ├── examples/ 19 runnable examples
2125+ ├── examples/ 23 runnable examples
19282126└── .github/workflows/ CI configuration
19292127```
0 commit comments