bc260y.c 54 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239124012411242124312441245124612471248124912501251125212531254125512561257125812591260126112621263126412651266126712681269127012711272127312741275127612771278127912801281128212831284128512861287128812891290129112921293129412951296129712981299130013011302130313041305130613071308130913101311131213131314131513161317131813191320132113221323132413251326132713281329133013311332133313341335133613371338133913401341134213431344134513461347134813491350135113521353135413551356135713581359136013611362136313641365136613671368136913701371137213731374137513761377137813791380138113821383138413851386138713881389139013911392139313941395139613971398139914001401140214031404140514061407140814091410141114121413141414151416141714181419142014211422142314241425142614271428142914301431143214331434143514361437143814391440144114421443144414451446144714481449145014511452145314541455145614571458145914601461146214631464146514661467146814691470147114721473147414751476147714781479148014811482148314841485148614871488148914901491149214931494149514961497149814991500150115021503150415051506150715081509151015111512151315141515151615171518151915201521152215231524152515261527152815291530153115321533153415351536153715381539154015411542154315441545154615471548154915501551155215531554155515561557155815591560156115621563156415651566156715681569157015711572157315741575157615771578157915801581158215831584158515861587158815891590159115921593159415951596159715981599160016011602160316041605160616071608160916101611161216131614161516161617161816191620162116221623162416251626162716281629163016311632163316341635163616371638163916401641164216431644164516461647164816491650165116521653165416551656165716581659166016611662166316641665166616671668166916701671167216731674167516761677167816791680168116821683168416851686168716881689169016911692169316941695169616971698169917001701170217031704170517061707170817091710171117121713171417151716171717181719172017211722172317241725172617271728172917301731173217331734173517361737173817391740174117421743174417451746174717481749175017511752175317541755175617571758175917601761176217631764176517661767176817691770177117721773177417751776177717781779178017811782178317841785178617871788178917901791179217931794179517961797179817991800180118021803180418051806180718081809181018111812181318141815181618171818181918201821182218231824182518261827182818291830183118321833183418351836183718381839184018411842184318441845184618471848184918501851185218531854185518561857185818591860186118621863186418651866186718681869187018711872187318741875187618771878187918801881188218831884188518861887188818891890189118921893189418951896189718981899190019011902190319041905190619071908190919101911191219131914191519161917191819191920192119221923192419251926192719281929193019311932193319341935193619371938193919401941194219431944194519461947194819491950195119521953195419551956195719581959196019611962196319641965196619671968196919701971197219731974197519761977197819791980198119821983198419851986198719881989199019911992199319941995199619971998199920002001200220032004200520062007200820092010201120122013201420152016201720182019202020212022202320242025202620272028202920302031203220332034203520362037203820392040204120422043204420452046204720482049205020512052205320542055205620572058205920602061206220632064206520662067206820692070207120722073207420752076207720782079208020812082208320842085208620872088208920902091209220932094209520962097209820992100210121022103210421052106210721082109211021112112211321142115211621172118211921202121212221232124212521262127212821292130213121322133213421352136213721382139214021412142214321442145214621472148214921502151215221532154215521562157215821592160216121622163216421652166216721682169217021712172217321742175217621772178217921802181218221832184218521862187218821892190219121922193219421952196219721982199220022012202220322042205220622072208220922102211221222132214221522162217221822192220222122222223222422252226222722282229223022312232223322342235
  1. #include "CONFIG.h"
  2. #if BC260Y
  3. /**
  4. ******************************************************************************
  5. * 版 本 :V1.0.0
  6. * 作 者 :liuyanbin,helomgxiang
  7. * 版权所有,盗版必究。
  8. * Copyright(C) All rights reserved
  9. ******************************************************************************
  10. * 历史记录
  11. * 序号 版本 变更内容 作者 日期
  12. * 1 V0.0.1 实现4GAT指令 何龙翔 2023/12/10
  13. * 2 V0.0.2 基于4实现NB指令 刘艳斌 2024/1/10
  14. * 3 V0.0.3 整合4g和nb代码 刘艳斌 2024/1/24
  15. * 4 V0.0.4 修改send函数添加sendrai 刘艳斌 2024/2/18
  16. ******************************************************************************
  17. */
  18. #include "stm32f10x.h"
  19. #include <stdio.h>
  20. #include <stdarg.h>
  21. #include <string.h>
  22. #include <stdlib.h>
  23. #include "CONFIG.h"
  24. #include "bc260y.h"
  25. #include "Log_Module.h"
  26. #include "At_Module.h"
  27. #include "Common_Util.h"
  28. // 方法声明
  29. void bc260y_reset(void); // 重置状态。该文件中的方法共用状态,在使用下面的方法前需要重置一下状态。
  30. enum Result bc260y_exit_sleep(void); // 退出休眠
  31. enum Result bc260y_exit_sleep_sync(void); // 退出休眠
  32. enum Result bc260y_exit_sleep_2(void); // 退出休眠
  33. enum Result bc260y_exit_sleep_2_sync(void); // 退出休眠
  34. void bc260y_enter_sleep(void); // 进入休眠
  35. /**
  36. * 查询休眠模式
  37. * 输入<<
  38. *
  39. * 输出>>
  40. * n 睡眠模式。0 禁用,默认;1 启用。
  41. **/
  42. enum Result bc260y_query_sleep(uint8_t * n); // 查询休眠模式。
  43. enum Result bc260y_query_sleep_sync(uint8_t * n); // 查询休眠模式。同步
  44. /**
  45. * 设置休眠模式
  46. * 输入<<
  47. * n 参数。0 禁用;1启用。
  48. * 输出>>
  49. *
  50. **/
  51. enum Result bc260y_set_sleep(uint8_t n); // 设置休眠模式。
  52. enum Result bc260y_set_sleep_sync(uint8_t n); // 设置休眠模式。同步
  53. /**
  54. * 设置功能模式
  55. * 输入<<
  56. * fun 0 最小功能模式;1 全功能模式。
  57. * 输出>>
  58. *
  59. **/
  60. enum Result bc260y_query_cfun(uint8_t * n); // 查询功能模式。
  61. enum Result bc260y_query_cfun_sync(uint8_t * n); // 查询功能模式。
  62. enum Result bc260y_set_cfun(uint8_t fun);
  63. enum Result bc260y_set_cfun_sync(uint8_t fun); // 同步
  64. /**
  65. * 设置ps域网络注册状态
  66. * 输入<<
  67. * n 0 禁止上报网络注册;1 允许上报网络注册;2 允许上报网络注册和位置信息
  68. * 输出>>
  69. *
  70. **/
  71. enum Result bc260y_set_cereg(uint8_t n);
  72. enum Result bc260y_set_cereg_sync(uint8_t n); // 同步
  73. /**
  74. * 查询ps域网络注册状态
  75. * 输入<<
  76. *
  77. * 输出>>
  78. * n 控制指定URC的上报。0 禁止上报网络注册;1 允许上报网络注册;2 允许上报网络注册和位置信息
  79. * stat 网络注册状态。0 未注册;1 已注册,归属地网络; 2 未注册;3 注册被拒绝;4 未知;5 已注册,漫游。
  80. * lac 基站位置区号。用于基站定位,2个字节。
  81. * ci 基站小区ID。用于基站定位,4个字节。
  82. *
  83. **/
  84. enum Result bc260y_query_cereg(uint8_t * n, uint8_t * stat, uint16_t * lac, uint32_t * ci);
  85. enum Result bc260y_query_cereg_sync(uint8_t * n, uint8_t * stat, uint16_t * lac, uint32_t * ci); // 同步
  86. /**
  87. * 查询socket服务状态
  88. * 输入<<
  89. * connectID Socket ID。范围1-11
  90. *
  91. * 输出>>
  92. * state Socket服务状态。0 未连接;1 正在连接;2 已建立连接;3 服务正在监听;4 连接断开。
  93. *
  94. *
  95. **/
  96. enum Result bc260y_query_socket_state(uint8_t connectID, uint8_t * state);
  97. enum Result bc260y_query_socket_state_sync(uint8_t connectID, uint8_t * state); // 同步
  98. /**
  99. * 打开socket服务
  100. * 输入<<
  101. * connectID Socket ID。范围1-11
  102. * service_type Socket服务类型。取值为"UDP", "TCP"。
  103. * IP_address 远程服务器地址
  104. * remote_port 远程服务器端口
  105. * access_mode Socket服务的数据访问模式。0 缓存模式;1 直吐模式;2 透传模式。
  106. *
  107. * 输出>>
  108. * err 操作错误代码。0 表示没有错误;其余参考移远文档。
  109. *
  110. **/
  111. enum Result bc260y_open_socket(uint8_t connectID, char * service_type, char * IP_address, uint16_t remote_port, uint8_t access_mode, uint16_t * err);
  112. enum Result bc260y_open_socket_sync(uint8_t connectID, char * service_type, char * IP_address, uint16_t remote_port, uint8_t access_mode, uint16_t * err); // 同步
  113. /**
  114. * 关闭socket服务
  115. * 输入<<
  116. * connectID Socket ID。范围1-11
  117. *
  118. * 输出>>
  119. *
  120. **/
  121. enum Result bc260y_close_socket(uint8_t connectID);
  122. enum Result bc260y_close_socket_sync(uint8_t connectID); // 同步
  123. /**
  124. * 解释:控制是否回显AT+QISEND要发送的数据
  125. * 为了便于处理返回,发送数据时需要关闭回显。
  126. * 输入<<
  127. * echo 是否回显AT+QISEND要发送的数据。0 不回显;1 回显。默认是回显
  128. *
  129. * 输出>>
  130. *
  131. **/
  132. enum Result bc260y_set_qisde(uint8_t echo);
  133. enum Result bc260y_set_qisde_sync(uint8_t echo); // 同步
  134. /**
  135. * 发送数据
  136. * 输入<<
  137. * connectID Socket ID。范围1-11。
  138. * send_length 发送长度。
  139. * data 待发送的数据。
  140. *
  141. *
  142. **/
  143. enum Result bc260y_send(uint8_t connectID, uint8_t * data, uint16_t data_length);
  144. enum Result bc260y_send_sync(uint8_t connectID, uint8_t * data, uint16_t data_length); // 同步
  145. enum Result bc260y_send_rai(uint8_t connectID, uint8_t * data, uint16_t data_length,uint8_t rai);
  146. enum Result bc260y_send_rai_sync(uint8_t connectID, uint8_t * data, uint16_t data_length,uint8_t rai);
  147. /**
  148. * 接收数据
  149. * 输入<<
  150. * connectID Socket ID。范围0-11。
  151. *
  152. * 输出>>
  153. * data 接收的数据。
  154. * data_length 接收的数据长度。
  155. **/
  156. enum Result bc260y_recv(uint8_t connectID, uint8_t * data, uint16_t * data_length); // 接收数据
  157. /**
  158. * 接收数据。带计时
  159. * 输入<<
  160. * connectID Socket ID。范围0-11。
  161. *
  162. * 输出>>
  163. * data 接收的数据。
  164. * data_length 接收的数据长度。
  165. *
  166. **/
  167. enum Result bc260y_recv_with_time(uint8_t connectID, uint8_t * data, uint16_t * data_length, uint32_t time_out);
  168. enum Result bc260y_recv_with_time_sync(uint8_t connectID, uint8_t * data, uint16_t * data_length, uint32_t time_out); // 同步
  169. /**
  170. * 解释:关闭模块
  171. * 关闭模块,关闭后会自动重启。
  172. * 输入<<
  173. * n 模块关机方式。0 立即关机;1 正常关机。默认是1
  174. *
  175. *
  176. **/
  177. enum Result bc260y_power_down(uint8_t n);
  178. enum Result bc260y_power_down_sync(uint8_t n); // 同步
  179. /**
  180. * 模块是否启动成功
  181. * 输入<<
  182. *
  183. * 输出>>
  184. *
  185. **/
  186. enum Result bc260y_ready(void);
  187. /**
  188. * 查询信号质量
  189. * 输入<<
  190. *
  191. * 输出>>
  192. * RSRP
  193. * RSRQ
  194. * RSSI
  195. * SINR
  196. **/
  197. enum Result bc260y_qeng_servingcell(int * RSRP, int * RSRQ, int * RSSI, int * SINR);
  198. enum Result bc260y_qeng_servingcell_sync(int * RSRP, int * RSRQ, int * RSSI, int * SINR);
  199. /**
  200. * 查询ICCID
  201. * 输入<<
  202. *
  203. * 输出>>
  204. * iccid SIM卡卡号
  205. **/
  206. enum Result bc260y_query_qccid(char * iccid);
  207. enum Result bc260y_query_qccid_sync(char * iccid);
  208. /**
  209. * 配置发送数据格式
  210. * 输入<<
  211. *n 0数据格式为文本字符串,1为十六进制字符串
  212. *
  213. **/
  214. enum Result bc260y_dataformat(uint8_t n);
  215. enum Result bc260y_dataformat_sync(uint8_t n);
  216. //
  217. /**
  218. * 查询dns
  219. **/
  220. enum Result bc260y_query_dns(char * pridnsaddr);
  221. enum Result bc260y_query_dns_sync(char * pridnsaddr);
  222. /**
  223. * 设置dns
  224. **/
  225. enum Result bc260y_set_dns(char * pridnsaddr, char * secdnsaddr);
  226. enum Result bc260y_set_dns_sync(char * pridnsaddr, char * secdnsaddr);
  227. // AT指令
  228. static char AT_CMD[1024];
  229. // EC800M提供的一些方法
  230. struct BC260Y_Struct bc260y =
  231. {
  232. .timer = {
  233. .time = 0,
  234. .flag = 0
  235. },
  236. .reset = bc260y_reset,
  237. .exit_sleep = bc260y_exit_sleep,
  238. .exit_sleep_sync = bc260y_exit_sleep_sync,
  239. .exit_sleep_2 = bc260y_exit_sleep_2,
  240. .exit_sleep_2_sync = bc260y_exit_sleep_2_sync,
  241. .enter_sleep = bc260y_enter_sleep,
  242. .query_sleep = bc260y_query_sleep,
  243. .query_sleep_sync = bc260y_query_sleep_sync,
  244. .set_sleep = bc260y_set_sleep,
  245. .set_sleep_sync = bc260y_set_sleep_sync,
  246. .query_cfun = bc260y_query_cfun,
  247. .query_cfun_sync = bc260y_query_cfun_sync,
  248. .set_cfun = bc260y_set_cfun,
  249. .set_cfun_sync = bc260y_set_cfun_sync,
  250. .set_cereg = bc260y_set_cereg,
  251. .set_cereg_sync = bc260y_set_cereg_sync,
  252. .query_cereg = bc260y_query_cereg,
  253. .query_cereg_sync = bc260y_query_cereg_sync,
  254. .query_socket_state = bc260y_query_socket_state,
  255. .query_socket_state_sync = bc260y_query_socket_state_sync,
  256. .open_socket = bc260y_open_socket,
  257. .open_socket_sync = bc260y_open_socket_sync,
  258. .close_socket = bc260y_close_socket,
  259. .close_socket_sync = bc260y_close_socket_sync,
  260. .set_qisde = bc260y_set_qisde,
  261. .set_qisde_sync = bc260y_set_qisde_sync,
  262. .send = bc260y_send,
  263. .send_sync = bc260y_send_sync,
  264. .send_rai = bc260y_send_rai,
  265. .send_rai_sync = bc260y_send_rai_sync,
  266. .recv = bc260y_recv,
  267. .recv_with_time = bc260y_recv_with_time,
  268. .recv_with_time_sync = bc260y_recv_with_time_sync,
  269. .power_down = bc260y_power_down,
  270. .power_down_sync = bc260y_power_down_sync,
  271. .ready = bc260y_ready,
  272. .qeng_servingcell = bc260y_qeng_servingcell,
  273. .qeng_servingcell_sync = bc260y_qeng_servingcell_sync,
  274. .query_qccid = bc260y_query_qccid,
  275. .query_qccid_sync = bc260y_query_qccid_sync,
  276. .dataformat= bc260y_dataformat,
  277. .dataformat_sync= bc260y_dataformat_sync,
  278. .query_dns = bc260y_query_dns,
  279. .query_dns_sync = bc260y_query_dns_sync,
  280. .set_dns = bc260y_set_dns,
  281. .set_dns_sync = bc260y_set_dns_sync,
  282. };
  283. // 发送AT指令
  284. static void send_data(uint8_t * data, uint16_t length)
  285. {
  286. // 发送AT指令
  287. AT_Send_Bytes(data, length);
  288. }
  289. // 发送AT指令
  290. static uint8_t send_at_string(char * cmd)
  291. {
  292. uint8_t state = 0;
  293. if(AT_Get_Status() == AT_Status_None)
  294. {
  295. // 发送AT指令
  296. AT_Send_String(cmd);
  297. state = 1;
  298. }
  299. return state;
  300. }
  301. // 获取状态
  302. static enum STATUS getStatus(void)
  303. {
  304. return bc260y.status;
  305. }
  306. // 设置状态
  307. static void setStatus(enum STATUS status)
  308. {
  309. bc260y.status = status;
  310. }
  311. // 获取定时
  312. static uint32_t getTimerMs(void)
  313. {
  314. return time_get_delay(&bc260y.timer);
  315. }
  316. // 清除定时
  317. static void clearTimer(void)
  318. {
  319. time_clear(&bc260y.timer);
  320. }
  321. // 设置定时
  322. //static void setTimerMs(uint32_t time)
  323. //{
  324. // bc260y.timer_ms = time;
  325. //}
  326. // 获取ID
  327. static uint8_t getActiveID(void)
  328. {
  329. return bc260y.activeID;
  330. }
  331. static void setActiveID(uint8_t activeID)
  332. {
  333. bc260y.activeID = activeID;
  334. }
  335. // 验证ID
  336. static uint8_t verifyActiveID(uint8_t activeID)
  337. {
  338. if(getActiveID() == 0 || getActiveID() == activeID){ return 1; }
  339. else
  340. {
  341. Log_Printf_Debug("activeID repetition!\r\n");
  342. return 0;
  343. }
  344. }
  345. // 返回超时结果
  346. static enum Result overtime(void)
  347. {
  348. setStatus(Status_Overtime); // 超时
  349. return Result_Failed; // 结果
  350. }
  351. // 返回成功结果
  352. static enum Result success(void)
  353. {
  354. // 成功
  355. setStatus(Status_Success);
  356. // 结果
  357. return Result_Success;
  358. }
  359. // 返回失败结果
  360. static enum Result failed(void)
  361. {
  362. // 失败
  363. setStatus(Status_Failed);
  364. // 失败结果
  365. return Result_Failed;
  366. }
  367. // 重置状态。该文件中的方法共用状态,在使用方法前需要重置一下状态。
  368. void bc260y_reset(void)
  369. {
  370. setStatus(Status_None); // 重置状态
  371. setActiveID(0); // 重置ID
  372. clearTimer(); // 重置计时
  373. AT_Clear(); // 清除AT指令
  374. }
  375. // 发送指令并改变状态
  376. enum Result send_at(char * cmd, uint8_t activeID)
  377. {
  378. Log_Printf_Debug(cmd); // 打印AT指令
  379. if(send_at_string(cmd)) // 发送AT指令
  380. {
  381. setActiveID(activeID); // 活动ID
  382. setStatus(Status_Sending); // 设置已发送
  383. clearTimer(); // 重置计时
  384. return Result_None; // 未知结果
  385. }
  386. else
  387. {
  388. Log_Printf_Debug("AT指令发送失败\r\n"); // 打印日志
  389. return Result_Failed; // 失败结果
  390. }
  391. }
  392. // 退出休眠
  393. enum Result bc260y_exit_sleep(void)
  394. {
  395. //GPIO_SetBits(WAKE_GPIO, WAKE_GPIO_Pin);// nb拉高io口,唤醒模组
  396. enum Result result = Result_None;
  397. int activeID = 1, time = 500; // 活动ID, 超时时间
  398. if(!verifyActiveID(activeID)){ return Result_Failed; } // 校验ID
  399. // 判断状态
  400. if(getStatus() == Status_None) // 空闲状态
  401. {
  402. sprintf(AT_CMD, "AT\r\n"); // 拼接AT指令
  403. result = send_at(AT_CMD, activeID);
  404. }
  405. else if(getStatus() != Status_Sending) // 上一次的结果没有清除,返回错误,为了保证时效性,需要重置状态。重新调用
  406. {
  407. Log_Printf_Debug("返回结果过期1,请重置状态\r\n"); // 打印日志
  408. result = failed(); // 失败
  409. }
  410. else if(getTimerMs() > time) // 正在发送状态。判断超时
  411. {
  412. Log_Printf_Debug("AT指令返回超时\r\n"); // 打印日志
  413. Log_SendArray_Debug(AT_result(), AT_result_length());
  414. result = overtime(); // 超时
  415. }
  416. if(strstr((char * )AT_result(), "OK\r\n") != NULL) // 查询是否返回
  417. {
  418. // 发送日志
  419. Log_Printf_Debug("AT返回: %d\r\n", AT_result_length());
  420. Log_SendArray_Debug(AT_result(), AT_result_length());
  421. result = success(); // 成功
  422. }
  423. else if(strstr((char * )AT_result(), "+QNBIOTEVENT:") != NULL)
  424. {
  425. // 发送日志
  426. Log_Printf_Debug("AT返回: %d\r\n", AT_result_length());
  427. Log_SendArray_Debug(AT_result(), AT_result_length());
  428. result = success(); // 成功
  429. }
  430. else if(strstr((char * )AT_result(), "ERROR\r\n") != NULL) // 查询是否返回
  431. {
  432. // 发送日志
  433. Log_Printf_Debug("AT返回: %d\r\n", AT_result_length());
  434. Log_SendArray_Debug(AT_result(), AT_result_length());
  435. result = failed(); // 失败
  436. }
  437. return result;
  438. }
  439. enum Result bc260y_exit_sleep_sync()
  440. {
  441. enum Result result = Result_None;
  442. while(1)
  443. {
  444. result = bc260y_exit_sleep();
  445. if(result != Result_None)
  446. {
  447. // 重置
  448. bc260y.reset();
  449. break;
  450. }
  451. }
  452. return result;
  453. }
  454. // 退出休眠
  455. enum Result bc260y_exit_sleep_2(void)
  456. {
  457. enum Result result = Result_None;
  458. int activeID = 123, time = 400; // 活动ID, 超时时间
  459. if(!verifyActiveID(activeID)){ return Result_Failed; } // 校验ID
  460. // 判断状态
  461. if(getStatus() == Status_None) // 空闲状态
  462. {
  463. sprintf(AT_CMD, "AT\r\n"); // 拼接AT指令
  464. result = send_at(AT_CMD, activeID);
  465. }
  466. else if(getStatus() != Status_Sending) // 上一次的结果没有清除,返回错误,为了保证时效性,需要重置状态。重新调用
  467. {
  468. Log_Printf_Debug("返回结果过期1,请重置状态\r\n"); // 打印日志
  469. result = failed(); // 失败
  470. }
  471. else if(getTimerMs() > time) // 正在发送状态。判断超时
  472. {
  473. Log_Printf_Debug("AT指令返回超时\r\n"); // 打印日志
  474. Log_SendArray_Debug(AT_result(), AT_result_length());
  475. result = success(); // 成功
  476. }
  477. if(strstr((char * )AT_result(), "OK\r\n") != NULL) // 查询是否返回
  478. {
  479. // 发送日志
  480. Log_Printf_Debug("AT返回: %d\r\n", AT_result_length());
  481. Log_SendArray_Debug(AT_result(), AT_result_length());
  482. result = success(); // 成功
  483. }
  484. else if(strstr((char * )AT_result(), "+QNBIOTEVENT:") != NULL)
  485. {
  486. // 发送日志
  487. Log_Printf_Debug("AT返回: %d\r\n", AT_result_length());
  488. Log_SendArray_Debug(AT_result(), AT_result_length());
  489. result = success(); // 成功
  490. }
  491. else if(strstr((char * )AT_result(), "ERROR\r\n") != NULL) // 查询是否返回
  492. {
  493. // 发送日志
  494. Log_Printf_Debug("AT返回: %d\r\n", AT_result_length());
  495. Log_SendArray_Debug(AT_result(), AT_result_length());
  496. result = failed(); // 失败
  497. }
  498. return result;
  499. }
  500. enum Result bc260y_exit_sleep_2_sync()
  501. {
  502. enum Result result = Result_None;
  503. while(1)
  504. {
  505. result = bc260y_exit_sleep_2();
  506. if(result != Result_None)
  507. {
  508. // 重置
  509. bc260y.reset();
  510. break;
  511. }
  512. }
  513. return result;
  514. }
  515. // 进入休眠
  516. void bc260y_enter_sleep(void)
  517. {
  518. // GPIO_ResetBits(WAKE_GPIO, WAKE_GPIO_Pin); // nb拉低io口,进入睡眠
  519. }
  520. /**
  521. * 查询休眠模式
  522. * 输入<<
  523. *
  524. * 输出>>
  525. * n 睡眠模式。0 禁用,默认;1 启用。
  526. *
  527. **/
  528. enum Result bc260y_query_sleep(uint8_t * n)
  529. {
  530. enum Result result = Result_None;
  531. int activeID = 1, time = 500; // 活动ID, 超时时间
  532. if(!verifyActiveID(activeID)){ return Result_Failed; } // 校验ID
  533. // 判断状态
  534. if(getStatus() == Status_None) // 空闲状态
  535. {
  536. sprintf(AT_CMD, "AT+QSCLK?\r\n"); // 拼接AT指令
  537. result = send_at(AT_CMD, activeID);
  538. }
  539. else if(getStatus() != Status_Sending) // 上一次的结果没有清除,返回错误,为了保证时效性,需要重置状态。重新调用
  540. {
  541. Log_Printf_Debug("返回结果过期1,请重置状态\r\n"); // 打印日志
  542. result = failed(); // 失败
  543. }
  544. else if(getTimerMs() > time) // 正在发送状态。判断超时
  545. {
  546. Log_Printf_Debug("AT指令返回超时\r\n"); // 打印日志
  547. result = overtime(); // 超时
  548. Log_SendArray_Debug(AT_result(), AT_result_length());
  549. }
  550. if(strstr((char * )AT_result(), "OK\r\n") != NULL) // 查询是否返回
  551. {
  552. // 发送日志
  553. Log_Printf_Debug("AT返回: %d\r\n", AT_result_length());
  554. Log_SendArray_Debug(AT_result(), AT_result_length());
  555. // 处理返回结果
  556. char * saveptr = NULL;
  557. char * split = "\r\n";
  558. // 第一行
  559. char * Line1 = strtok_r((char * )AT_result(), split, &saveptr);
  560. // 第二行
  561. char * Line2 = strtok_r(NULL, split, &saveptr);
  562. // 拆解第二行
  563. char * saveptr_inner = NULL;
  564. char * split_inner = ": ";
  565. strtok_r(Line2, split_inner, &saveptr_inner);
  566. // 获取mode
  567. * n = atoi(strtok_r(NULL, split_inner, &saveptr_inner));
  568. result = success(); // 成功
  569. }
  570. else if(strstr((char * )AT_result(), "ERROR\r\n") != NULL) // 查询是否返回
  571. {
  572. // 发送日志
  573. Log_Printf_Debug("AT返回: %d\r\n", AT_result_length());
  574. Log_SendArray_Debug(AT_result(), AT_result_length());
  575. result = failed(); // 失败
  576. }
  577. return result;
  578. }
  579. /**
  580. * 查询休眠模式。同步方法
  581. * 输入<<
  582. *
  583. * 输出>>
  584. * n 睡眠模式。0 禁用,默认;1 启用。
  585. *
  586. **/
  587. enum Result bc260y_query_sleep_sync(uint8_t * n)
  588. {
  589. enum Result result = Result_None;
  590. while(1)
  591. {
  592. result = bc260y_query_sleep(n);
  593. if(result != Result_None)
  594. {
  595. // 重置
  596. bc260y.reset();
  597. break;
  598. }
  599. }
  600. return result;
  601. }
  602. /**
  603. * 设置休眠模式
  604. * n 参数。0 禁用;1启用允许进入Deep Sleep 模式,2允许模块进入入Light Sleep 模式。
  605. **/
  606. enum Result bc260y_set_sleep(uint8_t n)
  607. {
  608. enum Result result = Result_None;
  609. int activeID = 2, time = 500; // 活动ID, 超时时间
  610. if(!verifyActiveID(activeID)){ return Result_Failed; } // 校验ID
  611. // 判断状态
  612. if(getStatus() == Status_None) // 空闲状态
  613. {
  614. sprintf(AT_CMD, "AT+QSCLK=%d\r\n", n); // 拼接AT指令
  615. result = send_at(AT_CMD, activeID);
  616. }
  617. else if(getStatus() != Status_Sending) // 上一次的结果没有清除,返回错误,为了保证时效性,需要重置状态。重新调用
  618. {
  619. Log_Printf_Debug("返回结果过期,请重置状态\r\n"); // 打印日志
  620. result = failed(); // 失败
  621. }
  622. else if(getTimerMs() > time) // 正在发送状态。判断超时
  623. {
  624. Log_Printf_Debug("AT指令返回超时\r\n"); // 打印日志
  625. result = overtime(); // 超时
  626. }
  627. else if(strstr((char * )AT_result(), "OK\r\n") != NULL) // 查询是否返回
  628. {
  629. // 发送日志
  630. Log_Printf_Debug("AT返回: %d\r\n", AT_result_length());
  631. Log_SendArray_Debug(AT_result(), AT_result_length());
  632. result = success(); // 成功
  633. }
  634. else if(strstr((char * )AT_result(), "ERROR\r\n") != NULL) // 查询是否返回
  635. {
  636. // 发送日志
  637. Log_Printf_Debug("AT返回: %d\r\n", AT_result_length());
  638. Log_SendArray_Debug(AT_result(), AT_result_length());
  639. result = failed(); // 失败
  640. }
  641. return result;
  642. }
  643. /**
  644. * 设置休眠模式。同步
  645. * n 参数。0 禁用;1启用。
  646. **/
  647. enum Result bc260y_set_sleep_sync(uint8_t n)
  648. {
  649. enum Result result = Result_None;
  650. while(1)
  651. {
  652. result = bc260y_set_sleep(n);
  653. if(result != Result_None)
  654. {
  655. // 重置
  656. bc260y.reset();
  657. break;
  658. }
  659. }
  660. return result;
  661. }
  662. /**
  663. * 查询功能模式
  664. * 输入<<
  665. *
  666. * 输出>>
  667. * n 功能模式。0 最小功能模式,默认;1 全功能模式。
  668. *
  669. **/
  670. enum Result bc260y_query_cfun(uint8_t * n)
  671. {
  672. enum Result result = Result_None;
  673. int activeID = 100, time = 500; // 活动ID, 超时时间
  674. if(!verifyActiveID(activeID)){ return Result_Failed; } // 校验ID
  675. // 判断状态
  676. if(getStatus() == Status_None) // 空闲状态
  677. {
  678. sprintf(AT_CMD, "AT+CFUN?\r\n"); // 拼接AT指令
  679. result = send_at(AT_CMD, activeID);
  680. }
  681. else if(getStatus() != Status_Sending) // 上一次的结果没有清除,返回错误,为了保证时效性,需要重置状态。重新调用
  682. {
  683. Log_Printf_Debug("返回结果过期1,请重置状态\r\n"); // 打印日志
  684. result = failed(); // 失败
  685. }
  686. else if(getTimerMs() > time) // 正在发送状态。判断超时
  687. {
  688. Log_Printf_Debug("AT指令返回超时\r\n"); // 打印日志
  689. result = overtime(); // 超时
  690. Log_SendArray_Debug(AT_result(), AT_result_length());
  691. }
  692. if(strstr((char * )AT_result(), "OK\r\n") != NULL) // 查询是否返回
  693. {
  694. // 发送日志
  695. Log_Printf_Debug("AT返回: %d\r\n", AT_result_length());
  696. Log_SendArray_Debug(AT_result(), AT_result_length());
  697. // 处理返回结果
  698. char * saveptr = NULL;
  699. char * split = "\r\n";
  700. // 第一行
  701. strtok_r((char * )AT_result(), split, &saveptr);
  702. // 第二行
  703. char * Line2 = strtok_r(NULL, split, &saveptr);
  704. // 拆解第二行
  705. char * saveptr_inner = NULL;
  706. char * split_inner = ": ";
  707. strtok_r(Line2, split_inner, &saveptr_inner);
  708. // 获取mode
  709. * n = atoi(strtok_r(NULL, split_inner, &saveptr_inner));
  710. result = success(); // 成功
  711. }
  712. else if(strstr((char * )AT_result(), "ERROR\r\n") != NULL) // 查询是否返回
  713. {
  714. // 发送日志
  715. Log_Printf_Debug("AT返回: %d\r\n", AT_result_length());
  716. Log_SendArray_Debug(AT_result(), AT_result_length());
  717. result = failed(); // 失败
  718. }
  719. return result;
  720. }
  721. enum Result bc260y_query_cfun_sync(uint8_t * n)
  722. {
  723. enum Result result = Result_None;
  724. while(1)
  725. {
  726. result = bc260y_query_cfun(n);
  727. if(result != Result_None)
  728. {
  729. // 重置
  730. bc260y.reset();
  731. break;
  732. }
  733. }
  734. return result;
  735. }
  736. /**
  737. * 设置功能模式
  738. * fun 0 最小功能模式;1 全功能模式。
  739. **/
  740. enum Result bc260y_set_cfun(uint8_t fun)
  741. {
  742. enum Result result = Result_None;
  743. int activeID = 4, time; // 活动ID, 超时时间
  744. // 校验参数
  745. if(fun == 0){ time = 3000; }
  746. else if(fun == 1){ time = 10000; }
  747. else
  748. {
  749. Log_Printf_Debug("set_cfun params error!\r\n");
  750. return Result_Failed;
  751. }
  752. // 校验ID
  753. if(!verifyActiveID(activeID)){ return Result_Failed; }
  754. // 判断状态
  755. if(getStatus() == Status_None) // 空闲状态
  756. {
  757. sprintf(AT_CMD, "AT+CFUN=%d\r\n", fun); // 拼接AT指令
  758. result = send_at(AT_CMD, activeID);
  759. }
  760. else if(getStatus() != Status_Sending) // 上一次的结果没有清除,返回错误,为了保证时效性,需要重置状态。重新调用
  761. {
  762. Log_Printf_Debug("返回结果过期,请重置状态\r\n"); // 打印日志
  763. result = failed(); // 失败
  764. }
  765. else if(getTimerMs() > time) // 正在发送状态。判断超时
  766. {
  767. Log_Printf_Debug("AT指令返回超时\r\n"); // 打印日志
  768. Log_SendArray_Debug(AT_result(), AT_result_length());
  769. result = overtime(); // 超时
  770. }
  771. else if(fun == 1 && strstr((char * )AT_result(), "+IP:") != NULL) // 查询是否返回
  772. {
  773. // 防止接收不完整
  774. if(AT_wait_time() > 10) // 过10ms之后再取数据,避免数据截断。
  775. {
  776. // 发送日志
  777. Log_Printf_Debug("AT返回: %d\r\n", AT_result_length());
  778. Log_SendArray_Debug(AT_result(), AT_result_length());
  779. result = success(); // 成功
  780. }
  781. }
  782. else if(fun == 0 && strstr((char * )AT_result(), "+CPIN: NOT READY") != NULL) // 查询是否返回
  783. {
  784. // 防止接收不完整
  785. if(AT_wait_time() > 10) // 过10ms之后再取数据,避免数据截断。
  786. {
  787. // 发送日志
  788. Log_Printf_Debug("AT返回: %d\r\n", AT_result_length());
  789. Log_SendArray_Debug(AT_result(), AT_result_length());
  790. result = success(); // 成功
  791. }
  792. }
  793. else if(strstr((char * )AT_result(), "ERROR\r\n") != NULL) // 查询是否返回
  794. {
  795. // 发送日志
  796. Log_Printf_Debug("AT返回: %d\r\n", AT_result_length());
  797. Log_SendArray_Debug(AT_result(), AT_result_length());
  798. result = failed(); // 失败
  799. }
  800. return result;
  801. }
  802. /**
  803. * 设置功能模式
  804. * 输入<<
  805. * fun 0 最小功能模式;1 全功能模式。
  806. * 输出>>
  807. *
  808. **/
  809. enum Result bc260y_set_cfun_sync(uint8_t fun)
  810. {
  811. enum Result result = Result_None;
  812. while(1)
  813. {
  814. result = bc260y_set_cfun(fun);
  815. if(result != Result_None)
  816. {
  817. // 重置
  818. bc260y.reset();
  819. break;
  820. }
  821. }
  822. return result;
  823. }
  824. /**
  825. * 设置ps域网络注册状态
  826. * n 0 禁止上报网络注册;1 允许上报网络注册;2 允许上报网络注册和位置信息
  827. **/
  828. enum Result bc260y_set_cereg(uint8_t n)
  829. {
  830. enum Result result = Result_None;
  831. int activeID = 6, time = 500; // 活动ID, 超时时间
  832. // 校验参数
  833. if(n > 2)
  834. {
  835. Log_Printf_Debug("set_cgreg params error!\r\n");
  836. return Result_Failed;
  837. }
  838. // 校验ID
  839. if(!verifyActiveID(activeID)){ return Result_Failed; }
  840. // 判断状态
  841. if(getStatus() == Status_None) // 空闲状态
  842. {
  843. sprintf(AT_CMD, "AT+CEREG=%d\r\n", n); // 拼接AT指令
  844. result = send_at(AT_CMD, activeID);
  845. }
  846. else if(getStatus() != Status_Sending) // 上一次的结果没有清除,返回错误,为了保证时效性,需要重置状态。重新调用
  847. {
  848. Log_Printf_Debug("返回结果过期,请重置状态\r\n"); // 打印日志
  849. result = failed(); // 失败
  850. }
  851. else if(getTimerMs() > time) // 正在发送状态。判断超时
  852. {
  853. Log_Printf_Debug("AT指令返回超时\r\n"); // 打印日志
  854. result = overtime(); // 超时
  855. }
  856. else if(strstr((char * )AT_result(), "OK\r\n") != NULL) // 查询是否返回
  857. {
  858. // 发送日志
  859. Log_Printf_Debug("AT返回: %d\r\n", AT_result_length());
  860. Log_SendArray_Debug(AT_result(), AT_result_length());
  861. result = success(); // 成功
  862. }
  863. else if(strstr((char * )AT_result(), "ERROR\r\n") != NULL) // 查询是否返回
  864. {
  865. // 发送日志
  866. Log_Printf_Debug("AT返回: %d\r\n", AT_result_length());
  867. Log_SendArray_Debug(AT_result(), AT_result_length());
  868. result = failed(); // 失败
  869. }
  870. return result;
  871. }
  872. /**
  873. * 设置ps域网络注册状态
  874. * 输入<<
  875. * n 0 禁止上报网络注册;1 允许上报网络注册;2 允许上报网络注册和位置信息
  876. * 输出>>
  877. *
  878. **/
  879. enum Result bc260y_set_cereg_sync(uint8_t n)
  880. {
  881. enum Result result = Result_None;
  882. while(1)
  883. {
  884. result = bc260y_set_cereg(n);
  885. if(result != Result_None)
  886. {
  887. // 重置
  888. bc260y.reset();
  889. break;
  890. }
  891. }
  892. return result;
  893. }
  894. /**
  895. * 查询ps域网络注册状态
  896. * 输入<<
  897. *
  898. * 输出>>
  899. * n 控制指定URC的上报。0 禁止上报网络注册;1 允许上报网络注册;2 允许上报网络注册和位置信息
  900. * stat 网络注册状态。0 未注册;1 已注册,归属地网络; 2 未注册;3 注册被拒绝;4 未知;5 已注册,漫游。
  901. * lac 基站位置区号。用于基站定位,2个字节。
  902. * ci 基站小区ID。用于基站定位,4个字节。
  903. *
  904. **/
  905. enum Result bc260y_query_cereg(uint8_t * n, uint8_t * stat, uint16_t * lac, uint32_t * ci)
  906. {
  907. enum Result result = Result_None;
  908. int activeID = 9, time = 500; // 活动ID, 超时时间
  909. // 校验ID
  910. if(!verifyActiveID(activeID)){ return Result_Failed; }
  911. // 判断状态
  912. if(getStatus() == Status_None) // 空闲状态
  913. {
  914. sprintf(AT_CMD, "AT+CEREG?\r\n"); // 拼接AT指令
  915. result = send_at(AT_CMD, activeID);
  916. }
  917. else if(getStatus() != Status_Sending) // 上一次的结果没有清除,返回错误,为了保证时效性,需要重置状态。重新调用
  918. {
  919. Log_Printf_Debug("返回结果过期,请重置状态\r\n"); // 打印日志
  920. result = failed(); // 失败
  921. }
  922. else if(getTimerMs() > time) // 正在发送状态。判断超时
  923. {
  924. Log_Printf_Debug("AT指令返回超时\r\n"); // 打印日志
  925. result = overtime(); // 超时
  926. }
  927. else if(strstr((char * )AT_result(), "OK\r\n") != NULL) // 查询是否返回
  928. {
  929. // 发送日志
  930. Log_Printf_Debug("AT返回: %d\r\n", AT_result_length());
  931. Log_SendArray_Debug(AT_result(), AT_result_length());
  932. // 处理返回结果
  933. char * saveptr = NULL;
  934. char * split = "\r\n";
  935. // 第一行
  936. strtok_r((char * )AT_result(), split, &saveptr);
  937. // 第二行
  938. char * Line2 = strtok_r(NULL, split, &saveptr);
  939. char * saveptr_inner = NULL;
  940. char * split_inner = ": ,\"";
  941. strtok_r(Line2, split_inner, &saveptr_inner);
  942. * n = atoi(strtok_r(NULL, split_inner, &saveptr_inner));
  943. * stat = atoi(strtok_r(NULL, split_inner, &saveptr_inner));
  944. // Log_Printf_Debug("saveptr_inner: %s\r\n", Line2);
  945. * lac = strtoul(strtok_r(NULL, split_inner, &saveptr_inner), NULL, 16);
  946. * ci = strtoul(strtok_r(NULL, split_inner, &saveptr_inner), NULL, 16);
  947. // 打印
  948. Log_Printf_Debug("mode: %d, stat: %d, lac: %d, ci: %d\r\n", * n, * stat, * lac, * ci);
  949. result = success(); // 成功
  950. }
  951. else if(strstr((char * )AT_result(), "ERROR\r\n") != NULL) // 查询是否返回
  952. {
  953. // 发送日志
  954. Log_Printf_Debug("AT返回: %d\r\n", AT_result_length());
  955. Log_SendArray_Debug(AT_result(), AT_result_length());
  956. result = failed(); // 失败
  957. }
  958. return result;
  959. }
  960. /**
  961. * 查询ps域网络注册状态
  962. * 输入<<
  963. *
  964. * 输出>>
  965. * n 控制指定URC的上报。0 禁止上报网络注册;1 允许上报网络注册;2 允许上报网络注册和位置信息
  966. * stat 网络注册状态。0 未注册;1 已注册,归属地网络; 2 未注册;3 注册被拒绝;4 未知;5 已注册,漫游。
  967. * lac 基站位置区号。用于基站定位,2个字节。
  968. * ci 基站小区ID。用于基站定位,4个字节。
  969. *
  970. **/
  971. enum Result bc260y_query_cereg_sync(uint8_t * n, uint8_t * stat, uint16_t * lac, uint32_t * ci)
  972. {
  973. enum Result result = Result_None;
  974. while(1)
  975. {
  976. result = bc260y_query_cereg(n, stat, lac, ci);
  977. if(result != Result_None)
  978. {
  979. // 重置
  980. bc260y.reset();
  981. break;
  982. }
  983. }
  984. return result;
  985. }
  986. /**
  987. * 查询socket服务状态
  988. * connectID Socket ID。范围1-11
  989. * state Socket服务状态。0 未连接;1 正在连接;2 已建立连接;3 服务正在监听;4 连接断开。
  990. *
  991. * activeID 9
  992. **/
  993. enum Result bc260y_query_socket_state(uint8_t connectID, uint8_t * state)
  994. {
  995. enum Result result = Result_None;
  996. int activeID = 9, time = 500; // 活动ID, 超时时间
  997. // 校验ID
  998. if(!verifyActiveID(activeID)){ return Result_Failed; }
  999. // 判断状态
  1000. if(getStatus() == Status_None) // 空闲状态
  1001. {
  1002. sprintf(AT_CMD, "AT+QISTATE=1,%d\r\n", connectID); // 拼接AT指令
  1003. result = send_at(AT_CMD, activeID);
  1004. }
  1005. else if(getStatus() != Status_Sending) // 上一次的结果没有清除,返回错误,为了保证时效性,需要重置状态。重新调用
  1006. {
  1007. Log_Printf_Debug("返回结果过期,请重置状态\r\n"); // 打印日志
  1008. result = failed(); // 失败
  1009. }
  1010. else if(getTimerMs() > time) // 正在发送状态。判断超时
  1011. {
  1012. Log_Printf_Debug("AT指令返回超时\r\n"); // 打印日志
  1013. result = overtime(); // 超时
  1014. }
  1015. else if(strstr((char * )AT_result(), "OK\r\n") != NULL) // 查询是否返回
  1016. {
  1017. // 发送日志
  1018. Log_Printf_Debug("AT返回: %d\r\n", AT_result_length());
  1019. Log_SendArray_Debug(AT_result(), AT_result_length());
  1020. // 处理返回结果
  1021. char * saveptr = NULL;
  1022. char * split = "\r\n";
  1023. // 第一行
  1024. strtok_r((char * )AT_result(), split, &saveptr);
  1025. // 第二行
  1026. char * Line2 = strtok_r(NULL, split, &saveptr);
  1027. // 查询结果为空
  1028. if(strcmp(Line2, "OK") == 0){ * state = 0; }
  1029. else
  1030. {
  1031. // 拆解第二行
  1032. char * saveptr_inner = NULL;
  1033. char * split_inner = ": ,\"";
  1034. strtok_r(Line2, split_inner, &saveptr_inner);
  1035. strtok_r(NULL, split_inner, &saveptr_inner);
  1036. strtok_r(NULL, split_inner, &saveptr_inner);
  1037. strtok_r(NULL, split_inner, &saveptr_inner);
  1038. strtok_r(NULL, split_inner, &saveptr_inner);
  1039. strtok_r(NULL, split_inner, &saveptr_inner);
  1040. * state = atoi(strtok_r(NULL, split_inner, &saveptr_inner));
  1041. }
  1042. // 打印
  1043. Log_Printf_Debug("result: %d\r\n", * state);
  1044. result = success(); // 成功
  1045. }
  1046. else if(strstr((char * )AT_result(), "ERROR\r\n") != NULL) // 查询是否返回
  1047. {
  1048. // 发送日志
  1049. Log_Printf_Debug("AT返回: %d\r\n", AT_result_length());
  1050. Log_SendArray_Debug(AT_result(), AT_result_length());
  1051. result = failed(); // 失败
  1052. }
  1053. return result;
  1054. }
  1055. /**
  1056. * 查询socket服务状态
  1057. * connectID Socket ID。范围1-11
  1058. * state Socket服务状态。0 未连接;1 正在连接;2 已建立连接;3 服务正在监听;4 连接断开。
  1059. *
  1060. * activeID 9
  1061. **/
  1062. enum Result bc260y_query_socket_state_sync(uint8_t connectID, uint8_t * state)
  1063. {
  1064. enum Result result = Result_None;
  1065. while(1)
  1066. {
  1067. result = bc260y_query_socket_state(connectID, state);
  1068. if(result != Result_None)
  1069. {
  1070. // 重置
  1071. bc260y.reset();
  1072. break;
  1073. }
  1074. }
  1075. return result;
  1076. }
  1077. /**
  1078. * 打开socket服务
  1079. * 输入<<
  1080. * connectID Socket ID。范围1-11
  1081. * service_type Socket服务类型。取值为"UDP", "TCP"。
  1082. * IP_address 远程服务器地址
  1083. * remote_port 远程服务器端口
  1084. * access_mode Socket服务的数据访问模式。0 缓存模式;1 直吐模式;2 透传模式。
  1085. *
  1086. * 输出>>
  1087. * err 操作错误代码。0 表示没有错误;其余参考移远文档。
  1088. *
  1089. * activeID 19
  1090. **/
  1091. enum Result bc260y_open_socket(uint8_t connectID, char * service_type, char * IP_address, uint16_t remote_port, uint8_t access_mode, uint16_t * err)
  1092. {
  1093. enum Result result = Result_None;
  1094. int activeID = 19, time = 5000; // 活动ID, 超时时间
  1095. // 校验ID
  1096. if(!verifyActiveID(activeID)){ return Result_Failed; }
  1097. // 判断状态
  1098. if(getStatus() == Status_None) // 空闲状态
  1099. {
  1100. sprintf(AT_CMD, "AT+QIOPEN=0,%d,\"%s\",\"%s\",%d,%d,%d\r\n", connectID, service_type, IP_address, remote_port, 0, access_mode); // 拼接AT指令
  1101. result = send_at(AT_CMD, activeID);
  1102. }
  1103. else if(getStatus() != Status_Sending) // 上一次的结果没有清除,返回错误,为了保证时效性,需要重置状态。重新调用
  1104. {
  1105. Log_Printf_Debug("返回结果过期,请重置状态\r\n"); // 打印日志
  1106. result = failed(); // 失败
  1107. }
  1108. else if(getTimerMs() > time) // 正在发送状态。判断超时
  1109. {
  1110. Log_Printf_Debug("AT指令返回超时\r\n"); // 打印日志
  1111. result = overtime(); // 超时
  1112. }
  1113. else if(strstr((char * )AT_result(), "+QIOPEN: ") != NULL) // 查询是否返回
  1114. {
  1115. // 发送日志
  1116. Log_Printf_Debug("AT返回: %d\r\n", AT_result_length());
  1117. Log_SendArray_Debug(AT_result(), AT_result_length());//
  1118. // 处理返回结果
  1119. char * saveptr = NULL;
  1120. char * split = "\r\n";
  1121. // 第一行
  1122. strtok_r((char * )AT_result(), split, &saveptr);
  1123. // 第二行
  1124. char * Line2 = strtok_r(NULL, split, &saveptr);
  1125. // 第三行
  1126. char * Line3 = strtok_r(NULL, split, &saveptr);
  1127. // 查询结果为空
  1128. if(strcmp(Line2, "OK") == 0)
  1129. {
  1130. // 拆解第三行
  1131. char * saveptr_inner = NULL;
  1132. char * split_inner = ": ,\"";
  1133. strtok_r(Line3, split_inner, &saveptr_inner);
  1134. uint8_t connID = atoi(strtok_r(NULL, split_inner, &saveptr_inner));
  1135. * err = atoi(strtok_r(NULL, split_inner, &saveptr_inner));
  1136. Log_Printf_Debug("result: %d, %d\r\n", connID, * err);
  1137. }
  1138. result = success(); // 成功
  1139. }
  1140. else if(strstr((char * )AT_result(), "ERROR\r\n") != NULL) // 查询是否返回
  1141. {
  1142. // 发送日志
  1143. Log_Printf_Debug("AT返回: %d\r\n", AT_result_length());
  1144. Log_SendArray_Debug(AT_result(), AT_result_length());
  1145. result = failed(); // 失败
  1146. }
  1147. return result;
  1148. }
  1149. /**
  1150. * 打开socket服务
  1151. * 输入<<
  1152. * connectID Socket ID。范围1-11
  1153. * service_type Socket服务类型。取值为"UDP", "TCP"。
  1154. * IP_address 远程服务器地址
  1155. * remote_port 远程服务器端口
  1156. * access_mode Socket服务的数据访问模式。0 缓存模式;1 直吐模式;2 透传模式。
  1157. *
  1158. * 输出>>
  1159. * err 操作错误代码。0 表示没有错误;其余参考移远文档。
  1160. *
  1161. * activeID 19
  1162. **/
  1163. enum Result bc260y_open_socket_sync(uint8_t connectID, char * service_type, char * IP_address, uint16_t remote_port, uint8_t access_mode, uint16_t * err)
  1164. {
  1165. enum Result result = Result_None;
  1166. while(1)
  1167. {
  1168. result = bc260y_open_socket(connectID, service_type, IP_address, remote_port, access_mode, err);
  1169. if(result != Result_None)
  1170. {
  1171. // 重置
  1172. bc260y.reset();
  1173. break;
  1174. }
  1175. }
  1176. return result;
  1177. }
  1178. /**
  1179. * 关闭socket服务
  1180. * 输入<<
  1181. * connectID Socket ID。范围1-11
  1182. *
  1183. * activeID 29
  1184. **/
  1185. enum Result bc260y_close_socket(uint8_t connectID)
  1186. {
  1187. enum Result result = Result_None;
  1188. int activeID = 29, time = 500; // 活动ID, 超时时间
  1189. // 校验ID
  1190. if(!verifyActiveID(activeID)){ return Result_Failed; }
  1191. // 判断状态
  1192. if(getStatus() == Status_None) // 空闲状态
  1193. {
  1194. sprintf(AT_CMD, "AT+QICLOSE=%d\r\n", connectID); // 拼接AT指令
  1195. result = send_at(AT_CMD, activeID);
  1196. }
  1197. else if(getStatus() != Status_Sending) // 上一次的结果没有清除,返回错误,为了保证时效性,需要重置状态。重新调用
  1198. {
  1199. Log_Printf_Debug("返回结果过期,请重置状态\r\n"); // 打印日志
  1200. result = failed(); // 失败
  1201. }
  1202. else if(getTimerMs() > time) // 正在发送状态。判断超时
  1203. {
  1204. Log_Printf_Debug("AT指令返回超时\r\n"); // 打印日志
  1205. result = overtime(); // 超时
  1206. }
  1207. else if(strstr((char * )AT_result(), "OK\r\n") != NULL) // 查询是否返回
  1208. {
  1209. // 发送日志
  1210. Log_Printf_Debug("AT返回: %d\r\n", AT_result_length());
  1211. Log_SendArray_Debug(AT_result(), AT_result_length());
  1212. result = success(); // 成功
  1213. }
  1214. else if(strstr((char * )AT_result(), "ERROR\r\n") != NULL) // 查询是否返回
  1215. {
  1216. // 发送日志
  1217. Log_Printf_Debug("AT返回: %d\r\n", AT_result_length());
  1218. Log_SendArray_Debug(AT_result(), AT_result_length());
  1219. result = failed(); // 失败
  1220. }
  1221. return result;
  1222. }
  1223. /**
  1224. * 关闭socket服务
  1225. * 输入<<
  1226. * connectID Socket ID。范围1-11
  1227. *
  1228. * activeID 29
  1229. **/
  1230. enum Result bc260y_close_socket_sync(uint8_t connectID)
  1231. {
  1232. enum Result result = Result_None;
  1233. while(1)
  1234. {
  1235. result = bc260y_close_socket(connectID);
  1236. if(result != Result_None)
  1237. {
  1238. // 重置
  1239. bc260y.reset();
  1240. break;
  1241. }
  1242. }
  1243. return result;
  1244. }
  1245. /**
  1246. * 解释:控制是否回显AT+QISEND要发送的数据
  1247. * 为了便于处理返回,发送数据时需要关闭回显。
  1248. * 输入<<
  1249. * echo 是否回显AT+QISEND要发送的数据。0 不回显;1 回显。默认是回显
  1250. *
  1251. * activeID 45
  1252. **/
  1253. enum Result bc260y_set_qisde(uint8_t echo)
  1254. {
  1255. enum Result result = Result_None;
  1256. int activeID = 45, time = 1000; // 活动ID, 超时时间
  1257. // 校验ID
  1258. if(!verifyActiveID(activeID)){ return Result_Failed; }
  1259. // 判断状态
  1260. if(getStatus() == Status_None) // 空闲状态
  1261. {
  1262. sprintf(AT_CMD, "ATE%d\r\n", echo); // 拼接AT指令
  1263. result = send_at(AT_CMD, activeID);
  1264. }
  1265. else if(getStatus() != Status_Sending) // 上一次的结果没有清除,返回错误,为了保证时效性,需要重置状态。重新调用
  1266. {
  1267. Log_Printf_Debug("返回结果过期,请重置状态\r\n"); // 打印日志
  1268. result = failed(); // 失败
  1269. }
  1270. else if(getTimerMs() > time) // 正在发送状态。判断超时
  1271. {
  1272. Log_Printf_Debug("AT指令返回超时\r\n"); // 打印日志
  1273. result = overtime(); // 超时
  1274. }
  1275. else if(strstr((char * )AT_result(), "OK\r\n") != NULL) // 查询是否返回
  1276. {
  1277. // 发送日志
  1278. Log_Printf_Debug("AT返回: %d\r\n", AT_result_length());
  1279. Log_SendArray_Debug(AT_result(), AT_result_length());
  1280. result = success(); // 成功
  1281. }
  1282. else if(strstr((char * )AT_result(), "ERROR\r\n") != NULL) // 查询是否返回
  1283. {
  1284. // 发送日志
  1285. Log_Printf_Debug("AT返回: %d\r\n", AT_result_length());
  1286. Log_SendArray_Debug(AT_result(), AT_result_length());
  1287. result = failed(); // 失败
  1288. }
  1289. return result;
  1290. }
  1291. /**
  1292. * 解释:控制是否回显AT+QISEND要发送的数据
  1293. * 为了便于处理返回,发送数据时需要关闭回显。
  1294. * 输入<<
  1295. * echo 是否回显AT+QISEND要发送的数据。0 不回显;1 回显。默认是回显
  1296. *
  1297. * activeID 45
  1298. **/
  1299. enum Result bc260y_set_qisde_sync(uint8_t echo)
  1300. {
  1301. enum Result result = Result_None;
  1302. while(1)
  1303. {
  1304. result = bc260y_set_qisde(echo);
  1305. if(result != Result_None)
  1306. {
  1307. // 重置
  1308. bc260y.reset();
  1309. break;
  1310. }
  1311. }
  1312. return result;
  1313. }
  1314. /**
  1315. * 发送数据
  1316. * 输入<<
  1317. * connectID Socket ID。范围1-11。
  1318. * send_length 发送长度。
  1319. * data 待发送的数据。
  1320. *
  1321. * activeID 49
  1322. **/
  1323. enum Result bc260y_send(uint8_t connectID, uint8_t * data, uint16_t data_length)
  1324. {
  1325. enum Result result = Result_None;
  1326. int activeID = 49, time = 10000; // 活动ID, 超时时间
  1327. // 校验ID
  1328. if(!verifyActiveID(activeID)){ return Result_Failed; }
  1329. // 判断状态
  1330. if(getStatus() == Status_None) // 空闲状态
  1331. {
  1332. sprintf(AT_CMD, "AT+QISEND=%d,%d\r\n", connectID, data_length); // 拼接AT指令
  1333. result = send_at(AT_CMD, activeID);
  1334. }
  1335. else if(getStatus() != Status_Sending) // 上一次的结果没有清除,返回错误,为了保证时效性,需要重置状态。重新调用
  1336. {
  1337. Log_Printf_Debug("返回结果过期,请重置状态\r\n"); // 打印日志
  1338. result = failed(); // 失败
  1339. }
  1340. else if(getTimerMs() > time) // 正在发送状态。判断超时
  1341. {
  1342. Log_Printf_Debug("AT指令返回超时\r\n"); // 打印日志
  1343. result = overtime(); // 超时
  1344. }
  1345. else if(strstr((char * )AT_result(), ">") != NULL) // 有响应
  1346. {
  1347. // 发送日志
  1348. Log_Printf_Debug("AT6返回: %d\r\n", AT_result_length());
  1349. Log_SendArray_Debug(AT_result(), AT_result_length());
  1350. // Log_Printf_Debug("coap:\r\n");
  1351. // Log_SendHex(data, data_length);
  1352. // Log_Printf_Debug("\r\n");
  1353. // 发送数据
  1354. send_data(data, data_length);
  1355. // 清理一下AT返回结果缓存
  1356. AT_Clear_Result();
  1357. }
  1358. else if(strstr((char * )AT_result(), "SEND OK\r\n") != NULL) // 查询是否返回
  1359. {
  1360. // 发送日志
  1361. Log_Printf_Debug("AT返回: %d\r\n", AT_result_length());
  1362. Log_SendArray_Debug(AT_result(), AT_result_length());
  1363. result = success(); // 成功
  1364. }
  1365. else if(strstr((char * )AT_result(), "SEND FALL\r\n") != NULL) // 查询是否返回
  1366. {
  1367. // 发送日志
  1368. Log_Printf_Debug("AT返回: %d\r\n", AT_result_length());
  1369. Log_SendArray_Debug(AT_result(), AT_result_length());
  1370. result = failed(); // 失败
  1371. }
  1372. else if(strstr((char * )AT_result(), "ERROR\r\n") != NULL) // 查询是否返回
  1373. {
  1374. // 发送日志
  1375. Log_Printf_Debug("AT返回: %d\r\n", AT_result_length());
  1376. Log_SendArray_Debug(AT_result(), AT_result_length());
  1377. result = failed(); // 失败
  1378. }
  1379. return result;
  1380. }
  1381. /**
  1382. * 发送数据
  1383. * 输入<<
  1384. * connectID Socket ID。范围1-11。
  1385. * send_length 发送长度。
  1386. * data 待发送的数据。
  1387. *
  1388. * activeID 49
  1389. **/
  1390. enum Result bc260y_send_sync(uint8_t connectID, uint8_t * data, uint16_t data_length)
  1391. {
  1392. enum Result result = Result_None;
  1393. while(1)
  1394. {
  1395. result = bc260y_send(connectID, data, data_length);
  1396. if(result != Result_None)
  1397. {
  1398. // 重置
  1399. bc260y.reset();
  1400. break;
  1401. }
  1402. }
  1403. return result;
  1404. }
  1405. /**
  1406. * 发送数据
  1407. * 输入<<
  1408. * connectID Socket ID。范围1-11。
  1409. * send_length 发送长度。
  1410. * data 待发送的数据。
  1411. *rai 发送模式,0发送不释放RRC,1发送立即释放RRC,2发送返回释放RRC
  1412. * activeID 49
  1413. **/
  1414. enum Result bc260y_send_rai(uint8_t connectID, uint8_t * data, uint16_t data_length,uint8_t rai)
  1415. {
  1416. enum Result result = Result_None;
  1417. int activeID = 50, time = 10000; // 活动ID, 超时时间
  1418. // 校验ID
  1419. if(!verifyActiveID(activeID)){ return Result_Failed; }
  1420. // 判断状态
  1421. if(getStatus() == Status_None) // 空闲状态
  1422. {
  1423. memset(AT_CMD, 0, sizeof(AT_CMD));
  1424. sprintf(AT_CMD + strlen(AT_CMD), "AT+QISEND=%d,%d,", connectID, data_length); // 拼接AT指令
  1425. for(uint16_t i = 0; i < data_length; i++)
  1426. {
  1427. // sprintf(AT_CMD + strlen(AT_CMD), "%02X", *(data + i));
  1428. sprintf(AT_CMD + strlen(AT_CMD), "%02X", data[i]);
  1429. }
  1430. sprintf(AT_CMD + strlen(AT_CMD), ",%d\r\n", rai); // 拼接AT指令
  1431. result = send_at(AT_CMD, activeID);
  1432. }
  1433. else if(getStatus() != Status_Sending) // 上一次的结果没有清除,返回错误,为了保证时效性,需要重置状态。重新调用
  1434. {
  1435. Log_Printf_Debug("返回结果过期,请重置状态\r\n"); // 打印日志
  1436. result = failed(); // 失败
  1437. }
  1438. else if(getTimerMs() > time) // 正在发送状态。判断超时
  1439. {
  1440. Log_Printf_Debug("AT指令返回超时\r\n"); // 打印日志
  1441. result = overtime(); // 超时
  1442. }
  1443. else if(strstr((char * )AT_result(), "SEND OK\r\n") != NULL) // 查询是否返回
  1444. {
  1445. // 发送日志
  1446. Log_Printf_Debug("AT返回: %d\r\n", AT_result_length());
  1447. Log_SendArray_Debug(AT_result(), AT_result_length());
  1448. result = success(); // 成功
  1449. }
  1450. else if(strstr((char * )AT_result(), "SEND FALL\r\n") != NULL) // 查询是否返回
  1451. {
  1452. // 发送日志
  1453. Log_Printf_Debug("AT返回: %d\r\n", AT_result_length());
  1454. Log_SendArray_Debug(AT_result(), AT_result_length());
  1455. result = failed(); // 失败
  1456. }
  1457. else if(strstr((char * )AT_result(), "ERROR\r\n") != NULL) // 查询是否返回
  1458. {
  1459. // 发送日志
  1460. Log_Printf_Debug("AT返回: %d\r\n", AT_result_length());
  1461. Log_SendArray_Debug(AT_result(), AT_result_length());
  1462. result = failed(); // 失败
  1463. }
  1464. return result;
  1465. }
  1466. /**
  1467. * 发送数据
  1468. * 输入<<
  1469. * connectID Socket ID。范围1-11。
  1470. * send_length 发送长度。
  1471. * data 待发送的数据。
  1472. *
  1473. * activeID 49
  1474. **/
  1475. enum Result bc260y_send_rai_sync(uint8_t connectID, uint8_t * data, uint16_t data_length,uint8_t rai)
  1476. {
  1477. enum Result result = Result_None;
  1478. while(1)
  1479. {
  1480. result = bc260y_send_rai(connectID, data, data_length, rai);
  1481. if(result != Result_None)
  1482. {
  1483. // 重置
  1484. bc260y.reset();
  1485. break;
  1486. }
  1487. }
  1488. return result;
  1489. }
  1490. /**
  1491. * 接收数据
  1492. * 输入<<
  1493. * connectID Socket ID。范围0-11。
  1494. *
  1495. * 输出>>
  1496. * data 接收的数据。
  1497. * data_length 接收的数据长度。
  1498. *
  1499. **/
  1500. enum Result bc260y_recv(uint8_t connectID, uint8_t * data, uint16_t * data_length)
  1501. {
  1502. // 设置AT为使用中,防止被其他程序占用
  1503. AT_Set_Status(AT_Status_Using);
  1504. enum Result result = Result_None;
  1505. // 校验参数
  1506. if(connectID > 11)
  1507. {
  1508. Log_Printf_Debug("recv params error!\r\n");
  1509. return Result_Failed;
  1510. }
  1511. char cmp[20];
  1512. sprintf(cmp, "+QIURC: \"recv\",%d", connectID); // 拼接AT指令
  1513. // 判断是否接收到
  1514. if(strstr((char * )AT_result(), cmp) != NULL)
  1515. {
  1516. // 防止接收不完整
  1517. uint32_t last_time = AT_wait_time();
  1518. if(last_time > 10) // 过10ms之后再取数据,避免数据截断。
  1519. {
  1520. // 发送日志
  1521. Log_Printf_Debug("AT返回: %d, time_diff: %d\r\n", AT_result_length(), last_time);
  1522. // 分割结果,获取报文长度
  1523. char * saveptr = NULL;
  1524. char * split = ",";
  1525. strtok_r((char * )AT_result(), split, &saveptr);
  1526. strtok_r(NULL, split, &saveptr);
  1527. * data_length = strtoul(strtok_r(NULL, split, &saveptr), NULL, 10);
  1528. // 内存拷贝
  1529. memcpy(data,saveptr+1, *data_length);
  1530. // 成功
  1531. result = Result_Success;
  1532. // 清理一下AT返回结果缓存
  1533. AT_Clear_Result();
  1534. }
  1535. }
  1536. return result;
  1537. }
  1538. /**
  1539. * 接收数据。带计时
  1540. * 输入<<
  1541. * connectID Socket ID。范围0-11。
  1542. *
  1543. * 输出>>
  1544. * data 接收的数据。
  1545. * data_length 接收的数据长度。
  1546. *
  1547. **/
  1548. enum Result bc260y_recv_with_time(uint8_t connectID, uint8_t * data, uint16_t * data_length, uint32_t time_out)
  1549. {
  1550. enum Result result = Result_None;
  1551. int activeID = 59, time = time_out; // 活动ID, 超时时间
  1552. // 校验ID
  1553. if(!verifyActiveID(activeID)){ return Result_Failed; }
  1554. // 判断状态
  1555. if(getStatus() == Status_None) // 空闲状态
  1556. {
  1557. setStatus(Status_Sending);
  1558. }
  1559. else if(getStatus() != Status_Sending) // 上一次的结果没有清除,返回错误,为了保证时效性,需要重置状态。重新调用
  1560. {
  1561. Log_Printf_Debug("返回结果过期,请重置状态\r\n"); // 打印日志
  1562. result = failed(); // 失败
  1563. }
  1564. else if(getTimerMs() > time) // 正在发送状态。判断超时
  1565. {
  1566. Log_Printf_Debug("等待时间超时\r\n"); // 打印日志
  1567. result = overtime(); // 超时
  1568. Log_SendArray_Debug(AT_result(), AT_result_length());
  1569. }
  1570. else
  1571. {
  1572. // 接收数据
  1573. result = bc260y.recv(connectID, data, data_length);
  1574. if(result == Result_Success)
  1575. {
  1576. result = success(); // 成功
  1577. }
  1578. }
  1579. return result;
  1580. }
  1581. /**
  1582. * 接收数据。带计时
  1583. * 输入<<
  1584. * connectID Socket ID。范围0-11。
  1585. *
  1586. * 输出>>
  1587. * data 接收的数据。
  1588. * data_length 接收的数据长度。
  1589. *
  1590. **/
  1591. enum Result bc260y_recv_with_time_sync(uint8_t connectID, uint8_t * data, uint16_t * data_length, uint32_t time_out)
  1592. {
  1593. enum Result result = Result_None;
  1594. while(1)
  1595. {
  1596. result = bc260y_recv_with_time(connectID, data, data_length, time_out);
  1597. if(result != Result_None)
  1598. {
  1599. // 重置
  1600. bc260y.reset();
  1601. break;
  1602. }
  1603. }
  1604. return result;
  1605. }
  1606. /**
  1607. * 解释:关闭模块
  1608. * 关闭模块,关闭后会自动重启。
  1609. * 输入<<
  1610. * n 模块关机方式。0 立即关机;1 正常关机。默认是1
  1611. *
  1612. * activeID 69
  1613. **/
  1614. enum Result bc260y_power_down(uint8_t n)
  1615. {
  1616. enum Result result = Result_None;
  1617. int activeID = 69, time = 3000; // 活动ID, 超时时间
  1618. // 校验ID
  1619. if(!verifyActiveID(activeID)){ return Result_Failed; }
  1620. // 判断状态
  1621. if(getStatus() == Status_None) // 空闲状态
  1622. {
  1623. sprintf(AT_CMD, "AT+QPOWD=%d\r\n", n); // 拼接AT指令
  1624. result = send_at(AT_CMD, activeID);
  1625. }
  1626. else if(getStatus() != Status_Sending) // 上一次的结果没有清除,返回错误,为了保证时效性,需要重置状态。重新调用
  1627. {
  1628. Log_Printf_Debug("返回结果过期,请重置状态\r\n"); // 打印日志
  1629. result = failed(); // 失败
  1630. }
  1631. else if(getTimerMs() > time) // 正在发送状态。判断超时
  1632. {
  1633. Log_Printf_Debug("AT指令返回超时\r\n"); // 打印日志
  1634. result = overtime();
  1635. }
  1636. else if(strstr((char * )AT_result(), "POWERED DOWN\r\n") != NULL) // 查询是否返回
  1637. {
  1638. // 发送日志
  1639. Log_Printf_Debug("AT返回: %d\r\n", AT_result_length());
  1640. Log_SendArray_Debug(AT_result(), AT_result_length());
  1641. // 成功结果
  1642. result = success();
  1643. }
  1644. return result;
  1645. }
  1646. /**
  1647. * 解释:关闭模块。同步
  1648. * 关闭模块,关闭后会自动重启。
  1649. * 输入<<
  1650. * n 模块关机方式。0 立即关机;1 正常关机。默认是1
  1651. *
  1652. * activeID 69
  1653. **/
  1654. enum Result bc260y_power_down_sync(uint8_t n)
  1655. {
  1656. enum Result result = Result_None;
  1657. while(1)
  1658. {
  1659. result = bc260y_power_down(n);
  1660. if(result != Result_None)
  1661. {
  1662. // 重置
  1663. bc260y.reset();
  1664. break;
  1665. }
  1666. }
  1667. return result;
  1668. }
  1669. /**
  1670. * 模块是否启动成功
  1671. * 输入<<
  1672. *
  1673. * 输出>>
  1674. *
  1675. **/
  1676. enum Result bc260y_ready(void)
  1677. {
  1678. if(AT_Get_Status() != AT_Status_None)
  1679. {
  1680. return Result_None;
  1681. }
  1682. enum Result result = Result_None;
  1683. // 判断是否接收到
  1684. uint8_t RDY[5]="RDY";
  1685. if(memmem(AT_result(),AT_result_length(),RDY,strlen((char *)RDY)) != 0)
  1686. {
  1687. // 发送日志
  1688. Log_Printf_Debug("AT返回: %d\r\n", AT_result_length());
  1689. Log_SendArray_Debug(AT_result(), AT_result_length());
  1690. // 成功结果
  1691. result = Result_Success;
  1692. // 清理一下AT返回结果缓存
  1693. AT_Clear_Result();
  1694. }
  1695. return result;
  1696. }
  1697. /**
  1698. * 查询信号质量
  1699. * 输入<<
  1700. *
  1701. * 输出>>
  1702. * RSRP
  1703. * RSRQ
  1704. * RSSI
  1705. * SINR
  1706. **/
  1707. enum Result bc260y_qeng_servingcell(int * RSRP, int * RSRQ, int * RSSI, int * SINR)
  1708. {
  1709. enum Result result = Result_None;
  1710. int activeID = 71, time = 500; // 活动ID, 超时时间
  1711. // 校验ID
  1712. if(!verifyActiveID(activeID)){ return Result_Failed; }
  1713. // 判断状态
  1714. if(getStatus() == Status_None) // 空闲状态
  1715. {
  1716. //sprintf(AT_CMD, "AT+QENG=\"servingcell\"\r\n"); // 拼接AT指令
  1717. sprintf(AT_CMD, "AT+QENG=0\r\n"); // 拼接AT指令
  1718. result = send_at(AT_CMD, activeID);
  1719. }
  1720. else if(getStatus() != Status_Sending) // 上一次的结果没有清除,返回错误,为了保证时效性,需要重置状态。重新调用
  1721. {
  1722. Log_Printf_Debug("返回结果过期,请重置状态\r\n"); // 打印日志
  1723. result = failed(); // 失败
  1724. }
  1725. else if(getTimerMs() > time) // 正在发送状态。判断超时
  1726. {
  1727. Log_Printf_Debug("AT指令返回超时\r\n"); // 打印日志
  1728. result = overtime(); // 超时
  1729. }
  1730. else if(strstr((char * )AT_result(), "OK\r\n") != NULL) // 查询是否返回
  1731. {
  1732. // 发送日志
  1733. Log_Printf_Debug("AT返回: %d\r\n", AT_result_length());
  1734. Log_SendArray_Debug(AT_result(), AT_result_length());
  1735. // 处理返回结果
  1736. // char * saveptr = NULL;
  1737. // char * split = "\r\n";
  1738. char * saveptr_inner = NULL;
  1739. char * split_inner = ",\"";
  1740. strtok_r((char * )AT_result(), split_inner, &saveptr_inner);
  1741. strtok_r(NULL, split_inner, &saveptr_inner);
  1742. strtok_r(NULL, split_inner, &saveptr_inner);
  1743. strtok_r(NULL, split_inner, &saveptr_inner);
  1744. strtok_r(NULL, split_inner, &saveptr_inner);
  1745. * RSRP = atoi(strtok_r(NULL, split_inner, &saveptr_inner));
  1746. * RSRQ = atoi(strtok_r(NULL, split_inner, &saveptr_inner));
  1747. * RSSI = atoi(strtok_r(NULL, split_inner, &saveptr_inner));
  1748. * SINR = atoi(strtok_r(NULL, split_inner, &saveptr_inner));
  1749. // 打印
  1750. Log_Printf_Debug("RSRP: %d, RSRQ: %d, RSSI: %d, SINR: %d\r\n", * RSRP, * RSRQ, * RSSI, * SINR);
  1751. result = success(); // 成功
  1752. }
  1753. else if(strstr((char * )AT_result(), "ERROR\r\n") != NULL) // 查询是否返回
  1754. {
  1755. // 发送日志
  1756. Log_Printf_Debug("AT返回: %d\r\n", AT_result_length());
  1757. Log_SendArray_Debug(AT_result(), AT_result_length());
  1758. result = failed(); // 失败
  1759. }
  1760. return result;
  1761. }
  1762. enum Result bc260y_qeng_servingcell_sync(int * RSRP, int * RSRQ, int * RSSI, int * SINR)
  1763. {
  1764. enum Result result = Result_None;
  1765. while(1)
  1766. {
  1767. result = bc260y_qeng_servingcell(RSRP, RSRQ, RSSI, SINR);
  1768. if(result != Result_None)
  1769. {
  1770. // 重置
  1771. bc260y.reset();
  1772. break;
  1773. }
  1774. }
  1775. return result;
  1776. }
  1777. /**
  1778. * 查询ICCID
  1779. * 输入<<
  1780. *
  1781. * 输出>>
  1782. * iccid SIM卡卡号
  1783. **/
  1784. enum Result bc260y_query_qccid(char * iccid)
  1785. {
  1786. enum Result result = Result_None;
  1787. int activeID = 75, time = 500; // 活动ID, 超时时间
  1788. // 校验ID
  1789. if(!verifyActiveID(activeID)){ return Result_Failed; }
  1790. // 判断状态
  1791. if(getStatus() == Status_None) // 空闲状态
  1792. {
  1793. sprintf(AT_CMD, "AT+QCCID\r\n"); // 拼接AT指令
  1794. result = send_at(AT_CMD, activeID);
  1795. }
  1796. else if(getStatus() != Status_Sending) // 上一次的结果没有清除,返回错误,为了保证时效性,需要重置状态。重新调用
  1797. {
  1798. Log_Printf_Debug("返回结果过期,请重置状态\r\n"); // 打印日志
  1799. result = failed(); // 失败
  1800. }
  1801. else if(getTimerMs() > time) // 正在发送状态。判断超时
  1802. {
  1803. Log_Printf_Debug("AT指令返回超时\r\n"); // 打印日志
  1804. result = overtime(); // 超时
  1805. }
  1806. else if(strstr((char * )AT_result(), "OK\r\n") != NULL) // 查询是否返回
  1807. {
  1808. // 发送日志
  1809. Log_Printf_Debug("AT返回: %d\r\n", AT_result_length());
  1810. Log_SendArray_Debug(AT_result(), AT_result_length());
  1811. // 处理返回结果
  1812. char * saveptr = NULL;
  1813. char * split = "\r\n";
  1814. // 第一行
  1815. char * Line1 =strtok_r((char * )AT_result(), split, &saveptr);
  1816. // // 第二行
  1817. // char * Line2 = strtok_r(NULL, split, &saveptr);
  1818. // 拆解第二行
  1819. char * saveptr_inner = NULL;
  1820. char * split_inner = ": ,\"";
  1821. strtok_r(Line1, split_inner, &saveptr_inner);
  1822. // 字符串拷贝
  1823. strcpy(iccid, strtok_r(NULL, split_inner, &saveptr_inner));
  1824. // 打印
  1825. Log_Printf_Debug("ICCID: %s\r\n", iccid);
  1826. result = success(); // 成功
  1827. }
  1828. else if(strstr((char * )AT_result(), "ERROR\r\n") != NULL) // 查询是否返回
  1829. {
  1830. // 发送日志
  1831. Log_Printf_Debug("AT返回: %d\r\n", AT_result_length());
  1832. Log_SendArray_Debug(AT_result(), AT_result_length());
  1833. result = failed(); // 失败
  1834. }
  1835. return result;
  1836. }
  1837. enum Result bc260y_query_qccid_sync(char * iccid)
  1838. {
  1839. enum Result result = Result_None;
  1840. while(1)
  1841. {
  1842. result = bc260y_query_qccid(iccid);
  1843. if(result != Result_None)
  1844. {
  1845. // 重置
  1846. bc260y.reset();
  1847. break;
  1848. }
  1849. }
  1850. return result;
  1851. }
  1852. /**
  1853. * 配置发送数据格式
  1854. * 输入<<
  1855. *n 0数据格式为文本字符串,1为十六进制字符串
  1856. *
  1857. **/
  1858. enum Result bc260y_dataformat(uint8_t n)
  1859. {
  1860. enum Result result = Result_None;
  1861. int activeID = 2, time = 500; // 活动ID, 超时时间
  1862. if(!verifyActiveID(activeID)){ return Result_Failed; } // 校验ID
  1863. // 判断状态
  1864. if(getStatus() == Status_None) // 空闲状态
  1865. {
  1866. sprintf(AT_CMD, "AT+QICFG=dataformat,%d,%d\r\n", n,0); // 拼接AT指令
  1867. result = send_at(AT_CMD, activeID);
  1868. }
  1869. else if(getStatus() != Status_Sending) // 上一次的结果没有清除,返回错误,为了保证时效性,需要重置状态。重新调用
  1870. {
  1871. Log_Printf_Debug("返回结果过期,请重置状态\r\n"); // 打印日志
  1872. result = failed(); // 失败
  1873. }
  1874. else if(getTimerMs() > time) // 正在发送状态。判断超时
  1875. {
  1876. Log_Printf_Debug("AT指令返回超时\r\n"); // 打印日志
  1877. result = overtime(); // 超时
  1878. }
  1879. else if(strstr((char * )AT_result(), "OK\r\n") != NULL) // 查询是否返回
  1880. {
  1881. // 发送日志
  1882. Log_Printf_Debug("AT返回: %d\r\n", AT_result_length());
  1883. Log_SendArray_Debug(AT_result(), AT_result_length());
  1884. result = success(); // 成功
  1885. }
  1886. else if(strstr((char * )AT_result(), "ERROR\r\n") != NULL) // 查询是否返回
  1887. {
  1888. // 发送日志
  1889. Log_Printf_Debug("AT返回: %d\r\n", AT_result_length());
  1890. Log_SendArray_Debug(AT_result(), AT_result_length());
  1891. result = failed(); // 失败
  1892. }
  1893. return result;
  1894. }
  1895. /**
  1896. * 配置发送数据格式
  1897. * 输入<<
  1898. *n 0数据格式为文本字符串,1为十六进制字符串
  1899. *
  1900. **/
  1901. enum Result bc260y_dataformat_sync(uint8_t n)
  1902. {
  1903. enum Result result = Result_None;
  1904. while(1)
  1905. {
  1906. result =bc260y_dataformat(n);
  1907. if(result != Result_None)
  1908. {
  1909. // 重置
  1910. bc260y.reset();
  1911. break;
  1912. }
  1913. }
  1914. return result;
  1915. }
  1916. /**
  1917. * 查询dns
  1918. * 输入<<
  1919. *
  1920. * 输出>>
  1921. * dns dns服务器IP
  1922. **/
  1923. enum Result bc260y_query_dns(char * pridnsaddr)
  1924. {
  1925. enum Result result = Result_None;
  1926. int activeID = 87, time = 500; // 活动ID, 超时时间
  1927. // 校验ID
  1928. if(!verifyActiveID(activeID)){ return Result_Failed; }
  1929. // 判断状态
  1930. if(getStatus() == Status_None) // 空闲状态
  1931. {
  1932. sprintf(AT_CMD, "AT+QIDNSCFG=0\r\n"); // 拼接AT指令
  1933. result = send_at(AT_CMD, activeID);
  1934. }
  1935. else if(getStatus() != Status_Sending) // 上一次的结果没有清除,返回错误,为了保证时效性,需要重置状态。重新调用
  1936. {
  1937. Log_Printf_Debug("返回结果过期,请重置状态\r\n"); // 打印日志
  1938. result = failed(); // 失败
  1939. }
  1940. else if(getTimerMs() > time) // 正在发送状态。判断超时
  1941. {
  1942. Log_Printf_Debug("AT指令返回超时\r\n"); // 打印日志
  1943. result = overtime(); // 超时
  1944. }
  1945. else if(strstr((char * )AT_result(), "OK\r\n") != NULL) // 查询是否返回
  1946. {
  1947. // 发送日志
  1948. Log_Printf_Debug("AT返回: %d\r\n", AT_result_length());
  1949. Log_SendArray_Debug(AT_result(), AT_result_length());
  1950. // 处理返回结果
  1951. char * saveptr = NULL;
  1952. char * split = "\r\n";
  1953. // 第一行
  1954. char * Line1 =strtok_r((char * )AT_result(), split, &saveptr);
  1955. // // 第二行
  1956. char * Line2 = strtok_r(NULL, split, &saveptr);
  1957. // 拆解第二行
  1958. char * saveptr_inner = NULL;
  1959. char * split_inner = "\"";
  1960. strtok_r(Line2, split_inner, &saveptr_inner);
  1961. // 字符串拷贝
  1962. strcpy(pridnsaddr, strtok_r(NULL, split_inner, &saveptr_inner));
  1963. result = success(); // 成功
  1964. }
  1965. else if(strstr((char * )AT_result(), "ERROR\r\n") != NULL) // 查询是否返回
  1966. {
  1967. // 发送日志
  1968. Log_Printf_Debug("AT返回: %d\r\n", AT_result_length());
  1969. Log_SendArray_Debug(AT_result(), AT_result_length());
  1970. result = failed(); // 失败
  1971. }
  1972. return result;
  1973. }
  1974. enum Result bc260y_query_dns_sync(char * pridnsaddr)
  1975. {
  1976. enum Result result = Result_None;
  1977. while(1)
  1978. {
  1979. result = bc260y_query_dns(pridnsaddr);
  1980. if(result != Result_None)
  1981. {
  1982. // 重置
  1983. bc260y.reset();
  1984. break;
  1985. }
  1986. }
  1987. return result;
  1988. }
  1989. /**
  1990. * 设置dns
  1991. * 输入<<
  1992. * pridnsaddr 主dns服务器
  1993. * secdnsaddr 次dns服务器
  1994. * 输出>>
  1995. **/
  1996. enum Result bc260y_set_dns(char * pridnsaddr, char * secdnsaddr)
  1997. {
  1998. enum Result result = Result_None;
  1999. int activeID = 87, time = 500; // 活动ID, 超时时间
  2000. // 校验ID
  2001. if(!verifyActiveID(activeID)){ return Result_Failed; }
  2002. // 判断状态
  2003. if(getStatus() == Status_None) // 空闲状态
  2004. {
  2005. sprintf(AT_CMD, "AT+QIDNSCFG=0,\"%s\",\"%s\"\r\n", pridnsaddr, secdnsaddr); // 拼接AT指令
  2006. result = send_at(AT_CMD, activeID);
  2007. }
  2008. else if(getStatus() != Status_Sending) // 上一次的结果没有清除,返回错误,为了保证时效性,需要重置状态。重新调用
  2009. {
  2010. Log_Printf_Debug("返回结果过期,请重置状态\r\n"); // 打印日志
  2011. result = failed(); // 失败
  2012. }
  2013. else if(getTimerMs() > time) // 正在发送状态。判断超时
  2014. {
  2015. Log_Printf_Debug("AT指令返回超时\r\n"); // 打印日志
  2016. result = overtime(); // 超时
  2017. }
  2018. else if(strstr((char * )AT_result(), "OK\r\n") != NULL) // 查询是否返回
  2019. {
  2020. // 发送日志
  2021. Log_Printf_Debug("AT返回: %d\r\n", AT_result_length());
  2022. Log_SendArray_Debug(AT_result(), AT_result_length());
  2023. result = success(); // 成功
  2024. }
  2025. else if(strstr((char * )AT_result(), "ERROR\r\n") != NULL) // 查询是否返回
  2026. {
  2027. // 发送日志
  2028. Log_Printf_Debug("AT返回: %d\r\n", AT_result_length());
  2029. Log_SendArray_Debug(AT_result(), AT_result_length());
  2030. result = failed(); // 失败
  2031. }
  2032. return result;
  2033. }
  2034. enum Result bc260y_set_dns_sync(char * pridnsaddr, char * secdnsaddr)
  2035. {
  2036. enum Result result = Result_None;
  2037. while(1)
  2038. {
  2039. result = bc260y_set_dns(pridnsaddr, secdnsaddr);
  2040. if(result != Result_None)
  2041. {
  2042. // 重置
  2043. bc260y.reset();
  2044. break;
  2045. }
  2046. }
  2047. return result;
  2048. }
  2049. #endif