Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

C function parameter mysteriously drifted?

I am working a project using Samba 3.6.25. When I follow the source code of “smbclient” trying to build my own SMB server listing utility, I met a strange thing:

When I invoke a function, it skipped my first parameter and fill it with second one instead, and then the second the third, as so on.

The function I invoke is: cli_rpc_pipe_open_noauth_transport() in cli_pipe.c. I added some debug codes in it:

NTSTATUS cli_rpc_pipe_open_noauth_transport(struct cli_state *cli,
                        enum dcerpc_transport_t transport,
                        const struct ndr_syntax_id *interface,
                        struct rpc_pipe_client **presult)
{

    struct rpc_pipe_client *result;
    struct pipe_auth_data *auth;
    NTSTATUS status;

    status = cli_rpc_pipe_open(cli, transport, interface, &result);
    _DEBUG("cli = %p", cli);
    _DEBUG("transport = %p", transport);
    _DEBUG("interface = %p", interface);
    _DEBUG("presult = %p", presult);
    _DEBUG("cli->desthost = %p", cli->desthost);
    _DEBUG("cli->desthost = \"%s\"", cli->desthost);
    if (!NT_STATUS_IS_OK(status)) {
        return status;
    }
……

And this is how I call this function:

NTSTATUS _pipe_open_noauth(struct cli_state *cli, const struct ndr_syntax_id *intf, struct rpc_pipe_client **presult)
{
    SMBD_DEBUG("cli = %p", cli);
    SMBD_DEBUG("intf = %p", intf);
    SMBD_DEBUG("presult = %p", presult);
    SMBD_DEBUG("cli->desthost = %p", cli->desthost);
    SMBD_DEBUG("cli->desthost = \"%s\"", cli->desthost);
    return cli_rpc_pipe_open_noauth_transport(cli, 1, intf, presult);
}

Here is what I get in the console:

--- SMBD (util_smbclient.c, 117): cli = 0xdb2b20
--- SMBD (util_smbclient.c, 118): intf = 0xda31c0
--- SMBD (util_smbclient.c, 119): presult = 0x7fe9fdc8
--- SMBD (util_smbclient.c, 120): cli->desthost = 0xdd3a50
--- SMBD (util_smbclient.c, 121): cli->desthost = "192.168.1.125"
=== Samba (rpc_client/cli_pipe.c, 2873): cli = 0x1
=== Samba (rpc_client/cli_pipe.c, 2874): transport = 0xda31c0
=== Samba (rpc_client/cli_pipe.c, 2875): interface = 0x7fe9fdc8
=== Samba (rpc_client/cli_pipe.c, 2876): presult = 0xdaf3d0

It did not make sense! Noticed that the four parameters I passed are: 0xdb2b20, 0x1, 0xda31c0, 0x7fe9fdc8 But what cli_rpc_pipe_open_noauth_transport() got was: 0x1, 0xda31c0, 0x7fe9fdc8, 0xdaf3d0

It was quite obvious that the first parameter “0xdb2b20” was missing, and the second one had taken its place.

Do anyone know what was going on and how could I fix it?

Thank you very much in advance!

——— Additional information:

The toolchain I was using was mipsel-linux-uclibc-cc/ld/ar. I tried to objdump several target files to see what was going on.

I dumped my own program, here is the assembles invoking the function. Noticed that the four parameters were passed in sequence: a0, a1, a2, a3:

  409bf0:   8fdc0010    lw  gp,16(s8)
  409bf4:   8fc40020    lw  a0,32(s8)
  409bf8:   24050001    li  a1,1            # store “1” in a1
  409bfc:   8fc60024    lw  a2,36(s8)
  409c00:   8fc70028    lw  a3,40(s8)
  409c04:   8f99ab74    lw  t9,-21644(gp)
  409c08:   00000000    nop
  409c0c:   0320f809    jalr    t9
  409c10:   00000000    nop
  409c14:   8fdc0010    lw  gp,16(s8)
  409c18:   03c0e821    move    sp,s8
  409c1c:   8fbf001c    lw  ra,28(sp)
  409c20:   8fbe0018    lw  s8,24(sp)
  409c24:   03e00008    jr  ra
  409c28:   27bd0020    addiu   sp,sp,32

Then I dumped smbclient, which also invoked cli_rpc_pipe_open_noauth_transport(). Here came the problem: it seemed that a0 was NOT used to pass parameter!!!

<cli_rpc_pipe_open_noauth>:
              …
  487840:   8fdc0018    lw  gp,24(s8)
  487844:   8fc2003c    lw  v0,60(s8)
  487848:   00000000    nop
  48784c:   afa20010    sw  v0,16(sp)
  487850:   02002021    move    a0,s0
  487854:   8fc50034    lw  a1,52(s8)
  487858:   24060001    li  a2,1    # Here, the number “1” was stored in a2 instead of a1!!!
  48785c:   8fc70038    lw  a3,56(s8)
  487860:   8f99aed0    lw  t9,-20784(gp)
  487864:   00000000    nop
  487868:   0320f809    jalr    t9  # cli_rpc_pipe_open_noauth_transport()
  48786c:   00000000    nop
  487870:   8fdc0018    lw  gp,24(s8)
  487874:   02001021    move    v0,s0
  487878:   03c0e821    move    sp,s8
  48787c:   8fbf0028    lw  ra,40(sp)
  487880:   8fbe0024    lw  s8,36(sp)
  487884:   8fb00020    lw  s0,32(sp)
  487888:   03e00008    jr  ra
  48788c:   27bd0030    addiu   sp,sp,48

Finally I dump cli_rpc_pipe_open_noauth_transport() itself, appears that it worked in the way smbclient did:

0053bdac <cli_rpc_pipe_open_noauth_transport>:
  53bdac:   3c1c0087    lui gp,0x87
  53bdb0:   279c3624    addiu   gp,gp,13860
  53bdb4:   0399e021    addu    gp,gp,t9
  53bdb8:   27bdffc0    addiu   sp,sp,-64
  53bdbc:   afbf0038    sw  ra,56(sp)
  53bdc0:   afbe0034    sw  s8,52(sp)
  53bdc4:   afb00030    sw  s0,48(sp)
  53bdc8:   03a0f021    move    s8,sp
  53bdcc:   afbc0018    sw  gp,24(sp)
  53bdd0:   afc40040    sw  a0,64(s8)
  53bdd4:   afc50044    sw  a1,68(s8)
  53bdd8:   afc60048    sw  a2,72(s8)
  53bddc:   afc7004c    sw  a3,76(s8)
  53bde0:   8f848080    lw  a0,-32640(gp)
  53bde4:   00000000    nop
  53bde8:   24844da0    addiu   a0,a0,19872
  53bdec:   24050b39    li  a1,2873
  53bdf0:   8fc60044    lw  a2,68(s8)
  53bdf4:   8f99cab0    lw  t9,-13648(gp)
  53bdf8:   00000000    nop
  53bdfc:   0320f809    jalr    t9              <—— invoke cli_rpc_pipe_open()
  53be00:   00000000    nop

Additional information No.2 -- How I compile my program

  1. I downloaded Samba from the official FTP server.
  2. configure and make it (cross-compile)
  3. Find all .o file in "source3" directory, and then archive them all together in a single .a file.
  4. Create my own application, call Samba function mostly like its own program "smbclient" does, with many -I options which ensure the compiling works
  5. Link libsmbclient.a which Samba officially provided, and my own archived .a in Step 3.

Additional information No.3

The complete source of this repository: https://github.com/Andrew-M-C/SMB-CIFS_discovery

like image 924
Andrew Chang Avatar asked Nov 08 '22 05:11

Andrew Chang


1 Answers

Answer from questioner here:

I solved it. Actually I have not solved the problem itself, but tried another way to achieve my goal.

The older way I built my project is: firstly build Samba, then link Samba object and static library files outside Samba repository. This was when I met the problem.

I have changed the way I built: firstly override the original Samba "smbclient" codes with my own ones, then build Samba. Samba Makefile recognize my source file as smbclient source file and smoothly compile and link them. Finally, it worked.

Please refer to the GitHub repository I mentioned in the question.

like image 172
Andrew Chang Avatar answered Nov 15 '22 12:11

Andrew Chang