📄 obex_client.c
字号:
// Called by the obex-layer when some event occurs.//void obex_event(obex_t *handle, obex_object_t *object, int mode, int event, int obex_cmd, int obex_rsp){ switch (event) { case OBEX_EV_PROGRESS: //DBPRT("Made some progress..."); break; case OBEX_EV_ABORT: BTERROR("Request aborted!"); break; case OBEX_EV_REQDONE: request_done(handle, object, obex_cmd, obex_rsp); break; case OBEX_EV_REQHINT: /* Accept any command. Not rellay good, but this is a test-program :) */ //OBEX_ObjectSetRsp(object, OBEX_RSP_CONTINUE, OBEX_RSP_SUCCESS); break; case OBEX_EV_REQ: DBPRT("Command request (%02x)", obex_cmd); //server_request(handle, object, event, obex_cmd); break; case OBEX_EV_LINKERR: OBEX_TransportDisconnect(handle); BTERROR("Link broken!"); break; case OBEX_EV_STREAMEMPTY: writestream(handle, object); break; case OBEX_EV_STREAMAVAIL: readstream(handle, object); break; case OBEX_EV_PARSEERR: //OBEX_TransportDisconnect(handle); BTERROR("Parse Error!"); break; default: BTERROR("Unknown event %02x!", event); break; }}/* ----------------- OBEX client --------------------------- */obexclt_t *obex_connect(struct sockaddr_affix *sa, obex_target_t *target, int *err){ obex_object_t *oo; // OBEX Object obex_headerdata_t hv; obexclt_t *clt; clt = malloc(sizeof(obexclt_t)); if (clt == NULL) return NULL; memset(clt, 0, sizeof(obexclt_t)); /* set members */ clt->family = sa->family; clt->conid = -1; if (sa->family == PF_AFFIX) { clt->handle = OBEX_Init(OBEX_TRANS_FD, obex_event, 0); if (!clt->handle) { BTERROR( "OBEX_Init failed:%s", strerror(errno)); free(clt); return NULL; } // connect to the server DBPRT("Connecting to host %s ...\n", bda2str(&sa->bda)); clt->fd = socket(PF_AFFIX, SOCK_STREAM, BTPROTO_RFCOMM); if (clt->fd < 0) { BTERROR("socket(PF_AFFIX, ..) failed\n"); *err = clt->fd; free(clt); return NULL; } *err = connect(clt->fd, (struct sockaddr*)sa, sizeof(*sa)); if (*err < 0) { DBPRT("Unable to connect to remote side\n"); close(clt->fd); free(clt); return NULL; } FdOBEX_TransportSetup(clt->handle, clt->fd, clt->fd, 0); } else if (sa->family == PF_INET) { // tcpmode struct sockaddr_in *in_addr = (struct sockaddr_in*)sa; DBPRT("Using TCP transport: host = %s", inet_ntoa(in_addr->sin_addr)); if (!(clt->handle = OBEX_Init(OBEX_TRANS_INET, obex_event, 0))) { BTERROR( "OBEX_Init failed:%s", strerror(errno)); *err = -1; free(clt); return NULL; } // connect to the server *err = OBEX_TransportConnect(clt->handle, (struct sockaddr*)in_addr, sizeof(*in_addr)); if (*err < 0) { DBPRT("Unable to connect to the server\n"); free(clt); return NULL; } } else { *err = -1; free(clt); return NULL; } //printf("target: %p\n", target); OBEX_SetUserData(clt->handle, clt); // create new object oo = OBEX_ObjectNew(clt->handle, OBEX_CMD_CONNECT); if (target) { hv.bs = target->data; OBEX_ObjectAddHeader(clt->handle, oo, OBEX_HDR_TARGET, hv, target->len, 0); } *err = obex_request(clt, oo); DBPRT("Connection return code: %d, id: %d\n", *err, clt->conid); if (*err) goto exit; if (target && clt->conid == -1) { *err = OBEX_RSP_CONFLICT; goto exit; } DBPRT("Connection established\n"); return clt;exit: DBPRT("Unable to connect\n"); obex_disconnect(clt); return NULL; }int obex_disconnect(obexclt_t *clt){ int err; obex_object_t *oo; // OBEX Object // create new object oo = OBEX_ObjectNew(clt->handle, OBEX_CMD_DISCONNECT); err = obex_request(clt, oo); if (clt->family != PF_INET) { OBEX_Cleanup(clt->handle); close(clt->fd); } else OBEX_TransportDisconnect(clt->handle); free(clt); return 0;}static int getuname(char **uname, char *name){ int uname_len; if (!name) { *uname = NULL; return 0; } uname_len = (strlen(name) + 1) << 1; *uname = malloc(uname_len); if (!*uname) return -1; OBEX_CharToUnicode(*uname, name, uname_len); return uname_len;}int obex_put(obexclt_t *clt, char *local, char *remote, char *type){ int err; obex_object_t *oo; // OBEX Object obex_headerdata_t hv; char *uname; int uname_len; if (!type && !remote) return -1; uname_len = getuname(&uname, remote); if (uname_len < 0) return -1; if (local) { clt->sfd = open(local, O_RDONLY); if (clt->sfd < 0) { if (uname) free(uname); return clt->sfd; } clt->buf = malloc(OBEX_STREAM_CHUNK); if (!clt->buf) { if (uname) free(uname); close(clt->sfd); clt->sfd = -1; return -1; } } else { /* in a case of delete */ clt->sfd = -1; clt->buf = NULL; } clt->opcode = OBEX_PUT; DBPRT("Sending file: %s, path: %s, size: %d\n", local, remote, get_fdsize(clt->sfd)); // create new object oo = OBEX_ObjectNew(clt->handle, OBEX_CMD_PUT); if (clt->conid != -1) { hv.bq4 = clt->conid; OBEX_ObjectAddHeader(clt->handle, oo, OBEX_HDR_CONNECTION, hv, 4, 0); } if (uname) { hv.bs = uname; OBEX_ObjectAddHeader(clt->handle, oo, OBEX_HDR_NAME, hv, uname_len, 0); free(uname); } if (type) { hv.bs = type; OBEX_ObjectAddHeader(clt->handle, oo, OBEX_HDR_TYPE, hv, strlen(type) + 1, 0); } if (clt->sfd >= 0) { hv.bq4 = get_fdsize(clt->sfd); OBEX_ObjectAddHeader(clt->handle, oo, OBEX_HDR_LENGTH, hv, sizeof(uint32_t), 0); hv.bs = NULL; OBEX_ObjectAddHeader(clt->handle, oo, OBEX_HDR_BODY, hv, 0, OBEX_FL_STREAM_START); } err = obex_request(clt, oo); if (clt->buf) { free(clt->buf); clt->buf = NULL; } if (clt->sfd >= 0) { close(clt->sfd); clt->sfd = -1; } return err;}int obex_get(obexclt_t *clt, char *local, char *remote, char *type){ int err; obex_object_t *oo; // OBEX Object obex_headerdata_t hv; char *uname; int uname_len; if (!local || (!type && !remote)) return -1; uname_len = getuname(&uname, remote); if (uname_len < 0) return -1; clt->sfd = open(local, O_CREAT | O_WRONLY, 0600); if (clt->sfd < 0) { if (uname) free(uname); return clt->sfd; } clt->opcode = OBEX_GET; // create new object oo = OBEX_ObjectNew(clt->handle, OBEX_CMD_GET); if (clt->conid != -1) { hv.bq4 = clt->conid; OBEX_ObjectAddHeader(clt->handle, oo, OBEX_HDR_CONNECTION, hv, 4, 0); } if (uname) { hv.bs = uname; OBEX_ObjectAddHeader(clt->handle, oo, OBEX_HDR_NAME, hv, uname_len, 0); free(uname); } if (type) { hv.bs = type; OBEX_ObjectAddHeader(clt->handle, oo, OBEX_HDR_TYPE, hv, strlen(type)+1, 0); } OBEX_ObjectReadStream(clt->handle, oo, NULL); err = obex_request(clt, oo); close(clt->sfd); clt->sfd = -1; return err;} int __obex_setpath(obexclt_t *clt, char *path, int flags){ int err; obex_object_t *oo; // OBEX Object obex_headerdata_t hv; char *uname = NULL; int uname_len = 0, is_name; obex_setpath_hdr_t nonhdrdata; clt->opcode = OBEX_SETPATH; nonhdrdata.flags = 0x02; nonhdrdata.constants = 0; if (path == NULL || *path == '\0') { /* empty name. set to root */ uname = ""; uname_len = 0; is_name = 1; } else if (strcmp(path, "..") != 0) { uname_len = (strlen(path)+1)<<1; uname = malloc(uname_len); if (!uname){ return -1; } OBEX_CharToUnicode(uname, path, uname_len); is_name = 2; } else { // ".." nonhdrdata.flags = 0x03; is_name = 0; } if (flags & SETPATH_CREATE) { if (is_name < 2) return -EINVAL; nonhdrdata.flags &= ~0x02; } // create new object oo = OBEX_ObjectNew(clt->handle, OBEX_CMD_SETPATH); OBEX_ObjectSetNonHdrData(oo, (uint8_t*)&nonhdrdata, 2); hv.bq4 = clt->conid; OBEX_ObjectAddHeader(clt->handle, oo, OBEX_HDR_CONNECTION, hv, 4, 0); if (is_name) { DBPRT("Setting name: %d\n", uname_len); hv.bs = uname; OBEX_ObjectAddHeader(clt->handle, oo, OBEX_HDR_NAME, hv, uname_len, 0); } err = obex_request(clt, oo); if (is_name == 2) free(uname); return err;}/* ------------------- file transfer API --------------------- */int obex_get_file(obexclt_t *clt, char *local, char *remote){ int err; char *pathc = NULL; if (!remote) return -1; if (!local) { pathc = strdup(remote); if (!pathc) return -1; local = basename(pathc); } err = obex_get(clt, local, remote, NULL); if (pathc) free(pathc); return err;}int obex_put_file(obexclt_t *clt, char *local, char *remote){ int err; char *pathc = NULL; if (!local) return -1; if (!remote) { pathc = strdup(local); if (!pathc) return -1; remote = basename(pathc); } err = obex_put(clt, local, remote, NULL); if (pathc) free(pathc); return err;}int obex_remove(obexclt_t *clt, char *name){ int err; err = obex_put(clt, NULL, name, NULL); return err;}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -