summaryrefslogtreecommitdiff
path: root/sys/src/cmd/aquarela/smbrap2client.c
diff options
context:
space:
mode:
authorTaru Karttunen <taruti@taruti.net>2011-03-30 15:46:40 +0300
committerTaru Karttunen <taruti@taruti.net>2011-03-30 15:46:40 +0300
commite5888a1ffdae813d7575f5fb02275c6bb07e5199 (patch)
treed8d51eac403f07814b9e936eed0c9a79195e2450 /sys/src/cmd/aquarela/smbrap2client.c
Import sources from 2011-03-30 iso image
Diffstat (limited to 'sys/src/cmd/aquarela/smbrap2client.c')
-rwxr-xr-xsys/src/cmd/aquarela/smbrap2client.c100
1 files changed, 100 insertions, 0 deletions
diff --git a/sys/src/cmd/aquarela/smbrap2client.c b/sys/src/cmd/aquarela/smbrap2client.c
new file mode 100755
index 000000000..3f3e182a3
--- /dev/null
+++ b/sys/src/cmd/aquarela/smbrap2client.c
@@ -0,0 +1,100 @@
+#include "headers.h"
+
+static SmbTransactionMethod smbtransactionmethodrap = {
+ .encodeprimary = smbtransactionencodeprimary,
+ .sendrequest = smbtransactionclientsend,
+ .receiveresponse = smbtransactionclientreceive,
+ .decoderesponse = smbtransactiondecoderesponse,
+};
+
+int
+smbclientrap(SmbClient *c, SmbBuffer *inparam, SmbBuffer *outparam, SmbBuffer *outdata, char **errmsgp)
+{
+ SmbTransaction transaction;
+ SmbHeader h;
+ memset(&transaction, 0, sizeof(transaction));
+ transaction.in.name = smbglobals.pipelanman;
+ transaction.in.parameters = smbbufferreadpointer(inparam);
+ transaction.in.tpcount = smbbufferreadspace(inparam);
+ transaction.in.maxpcount = smbbufferwritespace(outparam);
+ transaction.in.maxdcount = smbbufferwritespace(outdata);
+ transaction.out.parameters = outparam;
+ transaction.out.data = outdata;
+ h = c->protoh;
+ h.tid = c->ipctid;
+ h.mid = 0;
+ return smbtransactionexecute(&transaction, &h, &c->peerinfo, c->b, &smbtransactionmethodrap, c, nil, errmsgp);
+}
+
+int
+smbnetserverenum2(SmbClient *c, ulong stype, char *domain, int *entriesp, SmbRapServerInfo1 **sip, char **errmsgp)
+{
+ int rv;
+ ushort ec, entries, total, converter;
+ SmbRapServerInfo1 *si = nil;
+ SmbBuffer *ipb = smbbuffernew(512);
+ SmbBuffer *odb = smbbuffernew(65535);
+ SmbBuffer *opb = smbbuffernew(8);
+ smbbufferputs(ipb, 104);
+ smbbufferputstring(ipb, nil, SMB_STRING_ASCII, "WrLehDz");
+ smbbufferputstring(ipb, nil, SMB_STRING_ASCII, "B16BBDz");
+ smbbufferputs(ipb, 1);
+ smbbufferputs(ipb, smbbufferwritespace(odb));
+ smbbufferputl(ipb, stype);
+ smbbufferputstring(ipb, nil, SMB_STRING_ASCII, domain);
+ rv = !smbclientrap(c, ipb, opb, odb, errmsgp);
+ smbbufferfree(&ipb);
+ if (rv == 0) {
+ char *remark, *eremark;
+ int remarkspace;
+ int i;
+ if (!smbbuffergets(opb, &ec)
+ || !smbbuffergets(opb, &converter)
+ || !smbbuffergets(opb, &entries)
+ || !smbbuffergets(opb, &total)) {
+ smbstringprint(errmsgp, "smbnetserverenum2: not enough return parameters");
+ rv = -1;
+ goto done;
+ }
+ if (ec != 0) {
+ rv = ec;
+ goto done;
+ }
+ if (smbbufferreadspace(odb) < entries * 26) {
+ smbstringprint(errmsgp, "smbnetserverenum2: not enough return data");
+ rv = -1;
+ goto done;
+ }
+ remarkspace = smbbufferreadspace(odb) - entries * 26;
+ si = smbemalloc(entries * sizeof(SmbRapServerInfo1) + remarkspace);
+ remark = (char *)&si[entries];
+ eremark = remark + remarkspace;
+ for (i = 0; i < entries; i++) {
+ ulong offset;
+ int remarklen;
+ assert(smbbuffergetbytes(odb, si[i].name, 16));
+ assert(smbbuffergetb(odb, &si[i].vmaj));
+ assert(smbbuffergetb(odb, &si[i].vmin));
+ assert(smbbuffergetl(odb, &si[i].type));
+ assert(smbbuffergetl(odb, &offset));
+ offset -= converter;
+ if (!smbbufferoffsetcopystr(odb, offset, remark, eremark - remark, &remarklen)) {
+ smbstringprint(errmsgp, "smbnetserverenum2: invalid string offset");
+ rv = -1;
+ goto done;
+ }
+ si[i].remark = remark;
+ remark += remarklen;
+ }
+ *sip = si;
+ si = nil;
+ *entriesp = entries;
+ }
+ else
+ rv = -1;
+done:
+ free(si);
+ smbbufferfree(&opb);
+ smbbufferfree(&odb);
+ return rv;
+}