Skip to content

Support opening files for writing #19

Open

Description

@z3ntu

On Milos (SM7635) the ADSP seems to want to open a file for writing, and the sensors via libssc and iio-sensor-proxy don't work.

Tried to open /mnt/vendor/persist/sensors/registry/registry/DIR for writing

Briefly looking through hexagonrpcd/apps_std.c I don't quite understand how to get started on that, at least "mocking" that we're writing successfully. Can I just remove the check, or how does file access work with hexagonrpc?

(See also https://gitlab.postmarketos.org/postmarketOS/pmaports/-/merge_requests/7405#note_519034)

Activity

  1. flamingradian commented on Feb 15, 2026

    @flamingradian
    Collaborator

    File access is done through the apps_std interface with the relevant code in hexagonrpcd/apps_std.c and hexagonrpcd/interfaces/apps_std.def. I'm not sure if you already tried to remove the check, but the next step would be to implement apps_std_fwrite.

    FastRPC remote interfaces can be invoked from a different procesor (e.g. ADSP can invoke apps_std on CPU/AP, CPU/AP can invoke remotectl and sometimes chre_slpi on ADSP). Remote interfaces contain remote methods, which each have a parameter specification and a constant numeric ID. Remote method invocations send the handle to the remote interface, the remote method ID, 0-255 input buffers (parameters), and 0-255 output buffers (return values).

    When the DSP invokes the apps_std_fwrite remote method, HexagonRPCD (hexagonrpcd/listener.c) finds its metadata in the apps_std_procs array (indexed by remote method ID), does input validation, and calls the implementation with the plain buffer arrays. A stub implementation would only need to hardcode the data in outbufs.

    The remote method metadata can be found in the source code of Qualcomm's implementation (see the remote method ID then check _skel_method_23): https://github.com/qualcomm/fastrpc/blob/development/src/apps_std_skel.c#L1389. There isn't an automatic conversion for the parameter specification.

  2. z3ntu commented on Mar 6, 2026

    @z3ntu
    Author

    Thank you for the pointers! I think I've managed to get a bare minimum PoC with faking writes for now

    Tried to open /mnt/vendor/persist/sensors/registry/registry/DIR for writing, IGNORE                                                                                                                                                                                    
    openat($ADSP_LIBRARY_PATH, /mnt/vendor/persist/sensors/registry/registry/DIR) -> 3                                                                                                                                                                                     
    write(3, 3) -> 0                                                                                                                                                                                                                                                       
    data: 0x44 0x49 0x52                                                                                                               
    WARNING: Faking successful fwrite call for "DIR"!                                                                                  
    close(3)                                                                                                                           
    Could not open /mnt/vendor/persist/sensors/registry/sns_reg_version: No such file or directory                                     
    Tried to open /mnt/vendor/persist/sensors/registry/sns_reg_version for writing, IGNORE                                             
    Could not open /mnt/vendor/persist/sensors/registry/sns_reg_version: No such file or directory                                     
    

    https://github.com/z3ntu/hexagonrpc/tree/apps_std_fwrite

    z3ntu@e4b872b

    Maybe you could already take a look, in case I got some obvious basics wrong, but given it gets the parameters successfully, and seems to be happy with the response, I think that part is fine.

    Sidenote, took me a couple of hours until I got a basic understanding of the definition of HEXAGONRPC_DEFINE_REMOTE_METHOD and what I need to put in there. Not obvious for sure :)

  3. flamingradian commented on Mar 9, 2026

    @flamingradian
    Collaborator

    For the code change at first glance, I would expect at least a comment explaining why the expected input to apps_std_fwrite needs to be hardcoded. Pretending to write files is fine (like the way hexagonfs pretends to be an Android filesystem), but file operations are usually in hexagonfs and there is usually a data structure for what to do.

    Sidenote, took me a couple of hours until I got a basic understanding of the definition of HEXAGONRPC_DEFINE_REMOTE_METHOD and what I need to put in there. Not obvious for sure :)

    The skel file I linked would have been generated by QAIC from an IDL file. Some IDLs are FOSS so there is at least a baseline language. Would it be less confusing to be given the IDL from a reverse engineering tool? Is it more important to change the HexagonRPC method definition format with #13, or even to have a code generator like QAIC?

    apps_std_fwrite in apps_std.idl (manually reverse engineered):

    typedef long apps_std_FILE;
    
    interface apps_std {
    	/* 5 preceding remote methods */
    	long fwrite(in apps_std_FILE sin, in sequence<octet> buf, rout long bytesRead, rout long bEOF);
    }
    

    Method definition in proposed HexagonRPC format:

    static struct hrpc_arg_def_interp4 apps_std_stat_args[] = {
    	{ HRPC_ARG_WORD, sizeof(uint32_t) },
    	{ HRPC_ARG_BLOB_SEQ, sizeof(char) },
    	{ HRPC_ARG_OUT_BLOB, sizeof(uint32_t) },
    	{ HRPC_ARG_OUT_BLOB, sizeof(uint32_t) },
    };
    
    const struct hrpc_method_def_interp4 apps_std_stat_def = {
    	.msg_id = 5,
    	.n_args = HRPC_ARRAY_SIZE(apps_std_stat_args),
    	.args = apps_std_stat_args,
    	.n_inner_types = 0,
    	.inner_types = NULL,
    };
    
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions