pd692x0.c 37 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120112111221123112411251126112711281129113011311132113311341135113611371138113911401141114211431144114511461147114811491150115111521153115411551156115711581159116011611162116311641165116611671168116911701171117211731174117511761177117811791180118111821183118411851186118711881189119011911192119311941195119611971198119912001201120212031204120512061207120812091210121112121213121412151216121712181219122012211222122312241225122612271228122912301231123212331234123512361237123812391240124112421243124412451246124712481249125012511252125312541255125612571258125912601261126212631264126512661267126812691270127112721273127412751276127712781279128012811282128312841285128612871288128912901291129212931294129512961297129812991300130113021303130413051306130713081309131013111312131313141315131613171318131913201321132213231324132513261327132813291330133113321333133413351336133713381339134013411342134313441345134613471348134913501351135213531354135513561357135813591360136113621363136413651366136713681369137013711372137313741375137613771378137913801381138213831384138513861387138813891390139113921393139413951396139713981399140014011402140314041405140614071408140914101411141214131414141514161417141814191420142114221423142414251426142714281429143014311432143314341435143614371438143914401441144214431444144514461447144814491450145114521453145414551456145714581459146014611462146314641465146614671468146914701471147214731474147514761477147814791480148114821483148414851486148714881489149014911492149314941495149614971498149915001501150215031504150515061507150815091510151115121513
  1. // SPDX-License-Identifier: GPL-2.0-only
  2. /*
  3. * Driver for the Microchip PD692X0 PoE PSE Controller driver (I2C bus)
  4. *
  5. * Copyright (c) 2023 Bootlin, Kory Maincent <kory.maincent@bootlin.com>
  6. */
  7. #include <linux/delay.h>
  8. #include <linux/firmware.h>
  9. #include <linux/i2c.h>
  10. #include <linux/module.h>
  11. #include <linux/of.h>
  12. #include <linux/platform_device.h>
  13. #include <linux/pse-pd/pse.h>
  14. #define PD692X0_PSE_NAME "pd692x0_pse"
  15. #define PD692X0_MAX_PIS 48
  16. #define PD692X0_MAX_MANAGERS 12
  17. #define PD692X0_MAX_MANAGER_PORTS 8
  18. #define PD692X0_MAX_HW_PORTS (PD692X0_MAX_MANAGERS * PD692X0_MAX_MANAGER_PORTS)
  19. #define PD69200_BT_PROD_VER 24
  20. #define PD69210_BT_PROD_VER 26
  21. #define PD69220_BT_PROD_VER 29
  22. #define PD692X0_FW_MAJ_VER 3
  23. #define PD692X0_FW_MIN_VER 5
  24. #define PD692X0_FW_PATCH_VER 5
  25. enum pd692x0_fw_state {
  26. PD692X0_FW_UNKNOWN,
  27. PD692X0_FW_OK,
  28. PD692X0_FW_BROKEN,
  29. PD692X0_FW_NEED_UPDATE,
  30. PD692X0_FW_PREPARE,
  31. PD692X0_FW_WRITE,
  32. PD692X0_FW_COMPLETE,
  33. };
  34. struct pd692x0_msg {
  35. u8 key;
  36. u8 echo;
  37. u8 sub[3];
  38. u8 data[8];
  39. __be16 chksum;
  40. } __packed;
  41. struct pd692x0_msg_ver {
  42. u8 prod;
  43. u8 maj_sw_ver;
  44. u8 min_sw_ver;
  45. u8 pa_sw_ver;
  46. u8 param;
  47. u8 build;
  48. };
  49. enum {
  50. PD692X0_KEY_CMD,
  51. PD692X0_KEY_PRG,
  52. PD692X0_KEY_REQ,
  53. PD692X0_KEY_TLM,
  54. PD692X0_KEY_TEST,
  55. PD692X0_KEY_REPORT = 0x52
  56. };
  57. enum {
  58. PD692X0_MSG_RESET,
  59. PD692X0_MSG_GET_SYS_STATUS,
  60. PD692X0_MSG_GET_SW_VER,
  61. PD692X0_MSG_SET_TMP_PORT_MATRIX,
  62. PD692X0_MSG_PRG_PORT_MATRIX,
  63. PD692X0_MSG_SET_PORT_PARAM,
  64. PD692X0_MSG_GET_PORT_STATUS,
  65. PD692X0_MSG_DOWNLOAD_CMD,
  66. PD692X0_MSG_GET_PORT_CLASS,
  67. PD692X0_MSG_GET_PORT_MEAS,
  68. PD692X0_MSG_GET_PORT_PARAM,
  69. /* add new message above here */
  70. PD692X0_MSG_CNT
  71. };
  72. struct pd692x0_priv {
  73. struct i2c_client *client;
  74. struct pse_controller_dev pcdev;
  75. struct device_node *np;
  76. enum pd692x0_fw_state fw_state;
  77. struct fw_upload *fwl;
  78. bool cancel_request;
  79. u8 msg_id;
  80. bool last_cmd_key;
  81. unsigned long last_cmd_key_time;
  82. enum ethtool_c33_pse_admin_state admin_state[PD692X0_MAX_PIS];
  83. };
  84. /* Template list of communication messages. The non-null bytes defined here
  85. * constitute the fixed portion of the messages. The remaining bytes will
  86. * be configured later within the functions. Refer to the "PD692x0 BT Serial
  87. * Communication Protocol User Guide" for comprehensive details on messages
  88. * content.
  89. */
  90. static const struct pd692x0_msg pd692x0_msg_template_list[PD692X0_MSG_CNT] = {
  91. [PD692X0_MSG_RESET] = {
  92. .key = PD692X0_KEY_CMD,
  93. .sub = {0x07, 0x55, 0x00},
  94. .data = {0x55, 0x00, 0x55, 0x4e,
  95. 0x4e, 0x4e, 0x4e, 0x4e},
  96. },
  97. [PD692X0_MSG_GET_SYS_STATUS] = {
  98. .key = PD692X0_KEY_REQ,
  99. .sub = {0x07, 0xd0, 0x4e},
  100. .data = {0x4e, 0x4e, 0x4e, 0x4e,
  101. 0x4e, 0x4e, 0x4e, 0x4e},
  102. },
  103. [PD692X0_MSG_GET_SW_VER] = {
  104. .key = PD692X0_KEY_REQ,
  105. .sub = {0x07, 0x1e, 0x21},
  106. .data = {0x4e, 0x4e, 0x4e, 0x4e,
  107. 0x4e, 0x4e, 0x4e, 0x4e},
  108. },
  109. [PD692X0_MSG_SET_TMP_PORT_MATRIX] = {
  110. .key = PD692X0_KEY_CMD,
  111. .sub = {0x05, 0x43},
  112. .data = { 0, 0x4e, 0x4e, 0x4e,
  113. 0x4e, 0x4e, 0x4e, 0x4e},
  114. },
  115. [PD692X0_MSG_PRG_PORT_MATRIX] = {
  116. .key = PD692X0_KEY_CMD,
  117. .sub = {0x07, 0x43, 0x4e},
  118. .data = {0x4e, 0x4e, 0x4e, 0x4e,
  119. 0x4e, 0x4e, 0x4e, 0x4e},
  120. },
  121. [PD692X0_MSG_SET_PORT_PARAM] = {
  122. .key = PD692X0_KEY_CMD,
  123. .sub = {0x05, 0xc0},
  124. .data = { 0xf, 0xff, 0xff, 0xff,
  125. 0x4e, 0x4e, 0x4e, 0x4e},
  126. },
  127. [PD692X0_MSG_GET_PORT_STATUS] = {
  128. .key = PD692X0_KEY_REQ,
  129. .sub = {0x05, 0xc1},
  130. .data = {0x4e, 0x4e, 0x4e, 0x4e,
  131. 0x4e, 0x4e, 0x4e, 0x4e},
  132. },
  133. [PD692X0_MSG_DOWNLOAD_CMD] = {
  134. .key = PD692X0_KEY_PRG,
  135. .sub = {0xff, 0x99, 0x15},
  136. .data = {0x16, 0x16, 0x99, 0x4e,
  137. 0x4e, 0x4e, 0x4e, 0x4e},
  138. },
  139. [PD692X0_MSG_GET_PORT_CLASS] = {
  140. .key = PD692X0_KEY_REQ,
  141. .sub = {0x05, 0xc4},
  142. .data = {0x4e, 0x4e, 0x4e, 0x4e,
  143. 0x4e, 0x4e, 0x4e, 0x4e},
  144. },
  145. [PD692X0_MSG_GET_PORT_MEAS] = {
  146. .key = PD692X0_KEY_REQ,
  147. .sub = {0x05, 0xc5},
  148. .data = {0x4e, 0x4e, 0x4e, 0x4e,
  149. 0x4e, 0x4e, 0x4e, 0x4e},
  150. },
  151. [PD692X0_MSG_GET_PORT_PARAM] = {
  152. .key = PD692X0_KEY_REQ,
  153. .sub = {0x05, 0xc0},
  154. .data = {0x4e, 0x4e, 0x4e, 0x4e,
  155. 0x4e, 0x4e, 0x4e, 0x4e},
  156. },
  157. };
  158. static u8 pd692x0_build_msg(struct pd692x0_msg *msg, u8 echo)
  159. {
  160. u8 *data = (u8 *)msg;
  161. u16 chksum = 0;
  162. int i;
  163. msg->echo = echo++;
  164. if (echo == 0xff)
  165. echo = 0;
  166. for (i = 0; i < sizeof(*msg) - sizeof(msg->chksum); i++)
  167. chksum += data[i];
  168. msg->chksum = cpu_to_be16(chksum);
  169. return echo;
  170. }
  171. static int pd692x0_send_msg(struct pd692x0_priv *priv, struct pd692x0_msg *msg)
  172. {
  173. const struct i2c_client *client = priv->client;
  174. int ret;
  175. if (msg->key == PD692X0_KEY_CMD && priv->last_cmd_key) {
  176. int cmd_msleep;
  177. cmd_msleep = 30 - jiffies_to_msecs(jiffies - priv->last_cmd_key_time);
  178. if (cmd_msleep > 0)
  179. msleep(cmd_msleep);
  180. }
  181. /* Add echo and checksum bytes to the message */
  182. priv->msg_id = pd692x0_build_msg(msg, priv->msg_id);
  183. ret = i2c_master_send(client, (u8 *)msg, sizeof(*msg));
  184. if (ret != sizeof(*msg))
  185. return -EIO;
  186. return 0;
  187. }
  188. static int pd692x0_reset(struct pd692x0_priv *priv)
  189. {
  190. const struct i2c_client *client = priv->client;
  191. struct pd692x0_msg msg, buf = {0};
  192. int ret;
  193. msg = pd692x0_msg_template_list[PD692X0_MSG_RESET];
  194. ret = pd692x0_send_msg(priv, &msg);
  195. if (ret) {
  196. dev_err(&client->dev,
  197. "Failed to reset the controller (%pe)\n", ERR_PTR(ret));
  198. return ret;
  199. }
  200. msleep(30);
  201. ret = i2c_master_recv(client, (u8 *)&buf, sizeof(buf));
  202. if (ret != sizeof(buf))
  203. return ret < 0 ? ret : -EIO;
  204. /* Is the reply a successful report message */
  205. if (buf.key != PD692X0_KEY_REPORT || buf.sub[0] || buf.sub[1])
  206. return -EIO;
  207. msleep(300);
  208. ret = i2c_master_recv(client, (u8 *)&buf, sizeof(buf));
  209. if (ret != sizeof(buf))
  210. return ret < 0 ? ret : -EIO;
  211. /* Is the boot status without error */
  212. if (buf.key != 0x03 || buf.echo != 0xff || buf.sub[0] & 0x1) {
  213. dev_err(&client->dev, "PSE controller error\n");
  214. return -EIO;
  215. }
  216. return 0;
  217. }
  218. static bool pd692x0_try_recv_msg(const struct i2c_client *client,
  219. struct pd692x0_msg *msg,
  220. struct pd692x0_msg *buf)
  221. {
  222. /* Wait 30ms before readback as mandated by the protocol */
  223. msleep(30);
  224. memset(buf, 0, sizeof(*buf));
  225. i2c_master_recv(client, (u8 *)buf, sizeof(*buf));
  226. if (buf->key)
  227. return 0;
  228. msleep(100);
  229. memset(buf, 0, sizeof(*buf));
  230. i2c_master_recv(client, (u8 *)buf, sizeof(*buf));
  231. if (buf->key)
  232. return 0;
  233. return 1;
  234. }
  235. /* Implementation of I2C communication, specifically addressing scenarios
  236. * involving communication loss. Refer to the "Synchronization During
  237. * Communication Loss" section in the Communication Protocol document for
  238. * further details.
  239. */
  240. static int pd692x0_recv_msg(struct pd692x0_priv *priv,
  241. struct pd692x0_msg *msg,
  242. struct pd692x0_msg *buf)
  243. {
  244. const struct i2c_client *client = priv->client;
  245. int ret;
  246. ret = pd692x0_try_recv_msg(client, msg, buf);
  247. if (!ret)
  248. goto out_success;
  249. dev_warn(&client->dev,
  250. "Communication lost, rtnl is locked until communication is back!");
  251. ret = pd692x0_send_msg(priv, msg);
  252. if (ret)
  253. return ret;
  254. ret = pd692x0_try_recv_msg(client, msg, buf);
  255. if (!ret)
  256. goto out_success2;
  257. msleep(10000);
  258. ret = pd692x0_send_msg(priv, msg);
  259. if (ret)
  260. return ret;
  261. ret = pd692x0_try_recv_msg(client, msg, buf);
  262. if (!ret)
  263. goto out_success2;
  264. return pd692x0_reset(priv);
  265. out_success2:
  266. dev_warn(&client->dev, "Communication is back, rtnl is unlocked!");
  267. out_success:
  268. if (msg->key == PD692X0_KEY_CMD) {
  269. priv->last_cmd_key = true;
  270. priv->last_cmd_key_time = jiffies;
  271. } else {
  272. priv->last_cmd_key = false;
  273. }
  274. return 0;
  275. }
  276. static int pd692x0_sendrecv_msg(struct pd692x0_priv *priv,
  277. struct pd692x0_msg *msg,
  278. struct pd692x0_msg *buf)
  279. {
  280. struct device *dev = &priv->client->dev;
  281. int ret;
  282. ret = pd692x0_send_msg(priv, msg);
  283. if (ret)
  284. return ret;
  285. ret = pd692x0_recv_msg(priv, msg, buf);
  286. if (ret)
  287. return ret;
  288. if (msg->echo != buf->echo) {
  289. dev_err(dev,
  290. "Wrong match in message ID, expect %d received %d.\n",
  291. msg->echo, buf->echo);
  292. return -EIO;
  293. }
  294. /* If the reply is a report message is it successful */
  295. if (buf->key == PD692X0_KEY_REPORT &&
  296. (buf->sub[0] || buf->sub[1])) {
  297. return -EIO;
  298. }
  299. return 0;
  300. }
  301. static struct pd692x0_priv *to_pd692x0_priv(struct pse_controller_dev *pcdev)
  302. {
  303. return container_of(pcdev, struct pd692x0_priv, pcdev);
  304. }
  305. static int pd692x0_fw_unavailable(struct pd692x0_priv *priv)
  306. {
  307. switch (priv->fw_state) {
  308. case PD692X0_FW_OK:
  309. return 0;
  310. case PD692X0_FW_PREPARE:
  311. case PD692X0_FW_WRITE:
  312. case PD692X0_FW_COMPLETE:
  313. dev_err(&priv->client->dev, "Firmware update in progress!\n");
  314. return -EBUSY;
  315. case PD692X0_FW_BROKEN:
  316. case PD692X0_FW_NEED_UPDATE:
  317. default:
  318. dev_err(&priv->client->dev,
  319. "Firmware issue. Please update it!\n");
  320. return -EOPNOTSUPP;
  321. }
  322. }
  323. static int pd692x0_pi_enable(struct pse_controller_dev *pcdev, int id)
  324. {
  325. struct pd692x0_priv *priv = to_pd692x0_priv(pcdev);
  326. struct pd692x0_msg msg, buf = {0};
  327. int ret;
  328. ret = pd692x0_fw_unavailable(priv);
  329. if (ret)
  330. return ret;
  331. if (priv->admin_state[id] == ETHTOOL_C33_PSE_ADMIN_STATE_ENABLED)
  332. return 0;
  333. msg = pd692x0_msg_template_list[PD692X0_MSG_SET_PORT_PARAM];
  334. msg.data[0] = 0x1;
  335. msg.sub[2] = id;
  336. ret = pd692x0_sendrecv_msg(priv, &msg, &buf);
  337. if (ret < 0)
  338. return ret;
  339. priv->admin_state[id] = ETHTOOL_C33_PSE_ADMIN_STATE_ENABLED;
  340. return 0;
  341. }
  342. static int pd692x0_pi_disable(struct pse_controller_dev *pcdev, int id)
  343. {
  344. struct pd692x0_priv *priv = to_pd692x0_priv(pcdev);
  345. struct pd692x0_msg msg, buf = {0};
  346. int ret;
  347. ret = pd692x0_fw_unavailable(priv);
  348. if (ret)
  349. return ret;
  350. if (priv->admin_state[id] == ETHTOOL_C33_PSE_ADMIN_STATE_DISABLED)
  351. return 0;
  352. msg = pd692x0_msg_template_list[PD692X0_MSG_SET_PORT_PARAM];
  353. msg.data[0] = 0x0;
  354. msg.sub[2] = id;
  355. ret = pd692x0_sendrecv_msg(priv, &msg, &buf);
  356. if (ret < 0)
  357. return ret;
  358. priv->admin_state[id] = ETHTOOL_C33_PSE_ADMIN_STATE_DISABLED;
  359. return 0;
  360. }
  361. static int pd692x0_pi_is_enabled(struct pse_controller_dev *pcdev, int id)
  362. {
  363. struct pd692x0_priv *priv = to_pd692x0_priv(pcdev);
  364. struct pd692x0_msg msg, buf = {0};
  365. int ret;
  366. ret = pd692x0_fw_unavailable(priv);
  367. if (ret)
  368. return ret;
  369. msg = pd692x0_msg_template_list[PD692X0_MSG_GET_PORT_STATUS];
  370. msg.sub[2] = id;
  371. ret = pd692x0_sendrecv_msg(priv, &msg, &buf);
  372. if (ret < 0)
  373. return ret;
  374. if (buf.sub[1]) {
  375. priv->admin_state[id] = ETHTOOL_C33_PSE_ADMIN_STATE_ENABLED;
  376. return 1;
  377. } else {
  378. priv->admin_state[id] = ETHTOOL_C33_PSE_ADMIN_STATE_DISABLED;
  379. return 0;
  380. }
  381. }
  382. struct pd692x0_pse_ext_state_mapping {
  383. u32 status_code;
  384. enum ethtool_c33_pse_ext_state pse_ext_state;
  385. u32 pse_ext_substate;
  386. };
  387. static const struct pd692x0_pse_ext_state_mapping
  388. pd692x0_pse_ext_state_map[] = {
  389. {0x06, ETHTOOL_C33_PSE_EXT_STATE_OPTION_VPORT_LIM,
  390. ETHTOOL_C33_PSE_EXT_SUBSTATE_OPTION_VPORT_LIM_HIGH_VOLTAGE},
  391. {0x07, ETHTOOL_C33_PSE_EXT_STATE_OPTION_VPORT_LIM,
  392. ETHTOOL_C33_PSE_EXT_SUBSTATE_OPTION_VPORT_LIM_LOW_VOLTAGE},
  393. {0x08, ETHTOOL_C33_PSE_EXT_STATE_MR_PSE_ENABLE,
  394. ETHTOOL_C33_PSE_EXT_SUBSTATE_MR_PSE_ENABLE_DISABLE_PIN_ACTIVE},
  395. {0x0C, ETHTOOL_C33_PSE_EXT_STATE_ERROR_CONDITION,
  396. ETHTOOL_C33_PSE_EXT_SUBSTATE_ERROR_CONDITION_NON_EXISTING_PORT},
  397. {0x11, ETHTOOL_C33_PSE_EXT_STATE_ERROR_CONDITION,
  398. ETHTOOL_C33_PSE_EXT_SUBSTATE_ERROR_CONDITION_UNDEFINED_PORT},
  399. {0x12, ETHTOOL_C33_PSE_EXT_STATE_ERROR_CONDITION,
  400. ETHTOOL_C33_PSE_EXT_SUBSTATE_ERROR_CONDITION_INTERNAL_HW_FAULT},
  401. {0x1B, ETHTOOL_C33_PSE_EXT_STATE_OPTION_DETECT_TED,
  402. ETHTOOL_C33_PSE_EXT_SUBSTATE_OPTION_DETECT_TED_DET_IN_PROCESS},
  403. {0x1C, ETHTOOL_C33_PSE_EXT_STATE_ERROR_CONDITION,
  404. ETHTOOL_C33_PSE_EXT_SUBSTATE_ERROR_CONDITION_UNKNOWN_PORT_STATUS},
  405. {0x1E, ETHTOOL_C33_PSE_EXT_STATE_MR_MPS_VALID,
  406. ETHTOOL_C33_PSE_EXT_SUBSTATE_MR_MPS_VALID_DETECTED_UNDERLOAD},
  407. {0x1F, ETHTOOL_C33_PSE_EXT_STATE_OVLD_DETECTED,
  408. ETHTOOL_C33_PSE_EXT_SUBSTATE_OVLD_DETECTED_OVERLOAD},
  409. {0x20, ETHTOOL_C33_PSE_EXT_STATE_POWER_NOT_AVAILABLE,
  410. ETHTOOL_C33_PSE_EXT_SUBSTATE_POWER_NOT_AVAILABLE_BUDGET_EXCEEDED},
  411. {0x21, ETHTOOL_C33_PSE_EXT_STATE_ERROR_CONDITION,
  412. ETHTOOL_C33_PSE_EXT_SUBSTATE_ERROR_CONDITION_INTERNAL_HW_FAULT},
  413. {0x22, ETHTOOL_C33_PSE_EXT_STATE_ERROR_CONDITION,
  414. ETHTOOL_C33_PSE_EXT_SUBSTATE_ERROR_CONDITION_CONFIG_CHANGE},
  415. {0x24, ETHTOOL_C33_PSE_EXT_STATE_OPTION_VPORT_LIM,
  416. ETHTOOL_C33_PSE_EXT_SUBSTATE_OPTION_VPORT_LIM_VOLTAGE_INJECTION},
  417. {0x25, ETHTOOL_C33_PSE_EXT_STATE_ERROR_CONDITION,
  418. ETHTOOL_C33_PSE_EXT_SUBSTATE_ERROR_CONDITION_UNKNOWN_PORT_STATUS},
  419. {0x34, ETHTOOL_C33_PSE_EXT_STATE_SHORT_DETECTED,
  420. ETHTOOL_C33_PSE_EXT_SUBSTATE_SHORT_DETECTED_SHORT_CONDITION},
  421. {0x35, ETHTOOL_C33_PSE_EXT_STATE_ERROR_CONDITION,
  422. ETHTOOL_C33_PSE_EXT_SUBSTATE_ERROR_CONDITION_DETECTED_OVER_TEMP},
  423. {0x36, ETHTOOL_C33_PSE_EXT_STATE_ERROR_CONDITION,
  424. ETHTOOL_C33_PSE_EXT_SUBSTATE_ERROR_CONDITION_DETECTED_OVER_TEMP},
  425. {0x37, ETHTOOL_C33_PSE_EXT_STATE_ERROR_CONDITION,
  426. ETHTOOL_C33_PSE_EXT_SUBSTATE_ERROR_CONDITION_UNKNOWN_PORT_STATUS},
  427. {0x3C, ETHTOOL_C33_PSE_EXT_STATE_POWER_NOT_AVAILABLE,
  428. ETHTOOL_C33_PSE_EXT_SUBSTATE_POWER_NOT_AVAILABLE_PORT_PW_LIMIT_EXCEEDS_CONTROLLER_BUDGET},
  429. {0x3D, ETHTOOL_C33_PSE_EXT_STATE_POWER_NOT_AVAILABLE,
  430. ETHTOOL_C33_PSE_EXT_SUBSTATE_POWER_NOT_AVAILABLE_PD_REQUEST_EXCEEDS_PORT_LIMIT},
  431. {0x41, ETHTOOL_C33_PSE_EXT_STATE_POWER_NOT_AVAILABLE,
  432. ETHTOOL_C33_PSE_EXT_SUBSTATE_POWER_NOT_AVAILABLE_HW_PW_LIMIT},
  433. {0x43, ETHTOOL_C33_PSE_EXT_STATE_ERROR_CONDITION,
  434. ETHTOOL_C33_PSE_EXT_SUBSTATE_ERROR_CONDITION_UNKNOWN_PORT_STATUS},
  435. {0xA7, ETHTOOL_C33_PSE_EXT_STATE_OPTION_DETECT_TED,
  436. ETHTOOL_C33_PSE_EXT_SUBSTATE_OPTION_DETECT_TED_CONNECTION_CHECK_ERROR},
  437. {0xA8, ETHTOOL_C33_PSE_EXT_STATE_MR_MPS_VALID,
  438. ETHTOOL_C33_PSE_EXT_SUBSTATE_MR_MPS_VALID_CONNECTION_OPEN},
  439. { /* sentinel */ }
  440. };
  441. static void
  442. pd692x0_get_ext_state(struct ethtool_c33_pse_ext_state_info *c33_ext_state_info,
  443. u32 status_code)
  444. {
  445. const struct pd692x0_pse_ext_state_mapping *ext_state_map;
  446. ext_state_map = pd692x0_pse_ext_state_map;
  447. while (ext_state_map->status_code) {
  448. if (ext_state_map->status_code == status_code) {
  449. c33_ext_state_info->c33_pse_ext_state = ext_state_map->pse_ext_state;
  450. c33_ext_state_info->__c33_pse_ext_substate = ext_state_map->pse_ext_substate;
  451. return;
  452. }
  453. ext_state_map++;
  454. }
  455. }
  456. struct pd692x0_class_pw {
  457. int class;
  458. int class_cfg_value;
  459. int class_pw;
  460. int max_added_class_pw;
  461. };
  462. #define PD692X0_CLASS_PW_TABLE_SIZE 4
  463. /* 4/2 pairs class configuration power table in compliance mode.
  464. * Need to be arranged in ascending order of power support.
  465. */
  466. static const struct pd692x0_class_pw
  467. pd692x0_class_pw_table[PD692X0_CLASS_PW_TABLE_SIZE] = {
  468. {.class = 3, .class_cfg_value = 0x3, .class_pw = 15000, .max_added_class_pw = 3100},
  469. {.class = 4, .class_cfg_value = 0x2, .class_pw = 30000, .max_added_class_pw = 8000},
  470. {.class = 6, .class_cfg_value = 0x1, .class_pw = 60000, .max_added_class_pw = 5000},
  471. {.class = 8, .class_cfg_value = 0x0, .class_pw = 90000, .max_added_class_pw = 7500},
  472. };
  473. static int pd692x0_pi_get_pw_from_table(int op_mode, int added_pw)
  474. {
  475. const struct pd692x0_class_pw *pw_table;
  476. int i;
  477. pw_table = pd692x0_class_pw_table;
  478. for (i = 0; i < PD692X0_CLASS_PW_TABLE_SIZE; i++, pw_table++) {
  479. if (pw_table->class_cfg_value == op_mode)
  480. return pw_table->class_pw + added_pw * 100;
  481. }
  482. return -ERANGE;
  483. }
  484. static int pd692x0_pi_set_pw_from_table(struct device *dev,
  485. struct pd692x0_msg *msg, int pw)
  486. {
  487. const struct pd692x0_class_pw *pw_table;
  488. int i;
  489. pw_table = pd692x0_class_pw_table;
  490. if (pw < pw_table->class_pw) {
  491. dev_err(dev,
  492. "Power limit %dmW not supported. Ranges minimal available: [%d-%d]\n",
  493. pw,
  494. pw_table->class_pw,
  495. pw_table->class_pw + pw_table->max_added_class_pw);
  496. return -ERANGE;
  497. }
  498. for (i = 0; i < PD692X0_CLASS_PW_TABLE_SIZE; i++, pw_table++) {
  499. if (pw > (pw_table->class_pw + pw_table->max_added_class_pw))
  500. continue;
  501. if (pw < pw_table->class_pw) {
  502. dev_err(dev,
  503. "Power limit %dmW not supported. Ranges available: [%d-%d] or [%d-%d]\n",
  504. pw,
  505. (pw_table - 1)->class_pw,
  506. (pw_table - 1)->class_pw + (pw_table - 1)->max_added_class_pw,
  507. pw_table->class_pw,
  508. pw_table->class_pw + pw_table->max_added_class_pw);
  509. return -ERANGE;
  510. }
  511. msg->data[2] = pw_table->class_cfg_value;
  512. msg->data[3] = (pw - pw_table->class_pw) / 100;
  513. return 0;
  514. }
  515. pw_table--;
  516. dev_warn(dev,
  517. "Power limit %dmW not supported. Set to highest power limit %dmW\n",
  518. pw, pw_table->class_pw + pw_table->max_added_class_pw);
  519. msg->data[2] = pw_table->class_cfg_value;
  520. msg->data[3] = pw_table->max_added_class_pw / 100;
  521. return 0;
  522. }
  523. static int
  524. pd692x0_pi_get_pw_ranges(struct pse_control_status *st)
  525. {
  526. const struct pd692x0_class_pw *pw_table;
  527. int i;
  528. pw_table = pd692x0_class_pw_table;
  529. st->c33_pw_limit_ranges = kcalloc(PD692X0_CLASS_PW_TABLE_SIZE,
  530. sizeof(struct ethtool_c33_pse_pw_limit_range),
  531. GFP_KERNEL);
  532. if (!st->c33_pw_limit_ranges)
  533. return -ENOMEM;
  534. for (i = 0; i < PD692X0_CLASS_PW_TABLE_SIZE; i++, pw_table++) {
  535. st->c33_pw_limit_ranges[i].min = pw_table->class_pw;
  536. st->c33_pw_limit_ranges[i].max = pw_table->class_pw + pw_table->max_added_class_pw;
  537. }
  538. st->c33_pw_limit_nb_ranges = i;
  539. return 0;
  540. }
  541. static int pd692x0_ethtool_get_status(struct pse_controller_dev *pcdev,
  542. unsigned long id,
  543. struct netlink_ext_ack *extack,
  544. struct pse_control_status *status)
  545. {
  546. struct pd692x0_priv *priv = to_pd692x0_priv(pcdev);
  547. struct pd692x0_msg msg, buf = {0};
  548. u32 class;
  549. int ret;
  550. ret = pd692x0_fw_unavailable(priv);
  551. if (ret)
  552. return ret;
  553. msg = pd692x0_msg_template_list[PD692X0_MSG_GET_PORT_STATUS];
  554. msg.sub[2] = id;
  555. ret = pd692x0_sendrecv_msg(priv, &msg, &buf);
  556. if (ret < 0)
  557. return ret;
  558. /* Compare Port Status (Communication Protocol Document par. 7.1) */
  559. if ((buf.sub[0] & 0xf0) == 0x80 || (buf.sub[0] & 0xf0) == 0x90)
  560. status->c33_pw_status = ETHTOOL_C33_PSE_PW_D_STATUS_DELIVERING;
  561. else if (buf.sub[0] == 0x1b || buf.sub[0] == 0x22)
  562. status->c33_pw_status = ETHTOOL_C33_PSE_PW_D_STATUS_SEARCHING;
  563. else if (buf.sub[0] == 0x12)
  564. status->c33_pw_status = ETHTOOL_C33_PSE_PW_D_STATUS_FAULT;
  565. else
  566. status->c33_pw_status = ETHTOOL_C33_PSE_PW_D_STATUS_DISABLED;
  567. if (buf.sub[1])
  568. status->c33_admin_state = ETHTOOL_C33_PSE_ADMIN_STATE_ENABLED;
  569. else
  570. status->c33_admin_state = ETHTOOL_C33_PSE_ADMIN_STATE_DISABLED;
  571. priv->admin_state[id] = status->c33_admin_state;
  572. pd692x0_get_ext_state(&status->c33_ext_state_info, buf.sub[0]);
  573. status->c33_actual_pw = (buf.data[0] << 4 | buf.data[1]) * 100;
  574. msg = pd692x0_msg_template_list[PD692X0_MSG_GET_PORT_PARAM];
  575. msg.sub[2] = id;
  576. memset(&buf, 0, sizeof(buf));
  577. ret = pd692x0_sendrecv_msg(priv, &msg, &buf);
  578. if (ret < 0)
  579. return ret;
  580. ret = pd692x0_pi_get_pw_from_table(buf.data[0], buf.data[1]);
  581. if (ret < 0)
  582. return ret;
  583. status->c33_avail_pw_limit = ret;
  584. memset(&buf, 0, sizeof(buf));
  585. msg = pd692x0_msg_template_list[PD692X0_MSG_GET_PORT_CLASS];
  586. msg.sub[2] = id;
  587. ret = pd692x0_sendrecv_msg(priv, &msg, &buf);
  588. if (ret < 0)
  589. return ret;
  590. class = buf.data[3] >> 4;
  591. if (class <= 8)
  592. status->c33_pw_class = class;
  593. ret = pd692x0_pi_get_pw_ranges(status);
  594. if (ret < 0)
  595. return ret;
  596. return 0;
  597. }
  598. static struct pd692x0_msg_ver pd692x0_get_sw_version(struct pd692x0_priv *priv)
  599. {
  600. struct device *dev = &priv->client->dev;
  601. struct pd692x0_msg msg, buf = {0};
  602. struct pd692x0_msg_ver ver = {0};
  603. int ret;
  604. msg = pd692x0_msg_template_list[PD692X0_MSG_GET_SW_VER];
  605. ret = pd692x0_sendrecv_msg(priv, &msg, &buf);
  606. if (ret < 0) {
  607. dev_err(dev, "Failed to get PSE version (%pe)\n", ERR_PTR(ret));
  608. return ver;
  609. }
  610. /* Extract version from the message */
  611. ver.prod = buf.sub[2];
  612. ver.maj_sw_ver = (buf.data[0] << 8 | buf.data[1]) / 100;
  613. ver.min_sw_ver = ((buf.data[0] << 8 | buf.data[1]) / 10) % 10;
  614. ver.pa_sw_ver = (buf.data[0] << 8 | buf.data[1]) % 10;
  615. ver.param = buf.data[2];
  616. ver.build = buf.data[3];
  617. return ver;
  618. }
  619. struct pd692x0_manager {
  620. struct device_node *port_node[PD692X0_MAX_MANAGER_PORTS];
  621. int nports;
  622. };
  623. struct pd692x0_matrix {
  624. u8 hw_port_a;
  625. u8 hw_port_b;
  626. };
  627. static int
  628. pd692x0_of_get_ports_manager(struct pd692x0_priv *priv,
  629. struct pd692x0_manager *manager,
  630. struct device_node *np)
  631. {
  632. struct device_node *node;
  633. int ret, nports, i;
  634. nports = 0;
  635. for_each_child_of_node(np, node) {
  636. u32 port;
  637. if (!of_node_name_eq(node, "port"))
  638. continue;
  639. ret = of_property_read_u32(node, "reg", &port);
  640. if (ret)
  641. goto out;
  642. if (port >= PD692X0_MAX_MANAGER_PORTS || port != nports) {
  643. dev_err(&priv->client->dev,
  644. "wrong number or order of manager ports (%d)\n",
  645. port);
  646. ret = -EINVAL;
  647. goto out;
  648. }
  649. of_node_get(node);
  650. manager->port_node[port] = node;
  651. nports++;
  652. }
  653. manager->nports = nports;
  654. return 0;
  655. out:
  656. for (i = 0; i < nports; i++) {
  657. of_node_put(manager->port_node[i]);
  658. manager->port_node[i] = NULL;
  659. }
  660. of_node_put(node);
  661. return ret;
  662. }
  663. static int
  664. pd692x0_of_get_managers(struct pd692x0_priv *priv,
  665. struct pd692x0_manager manager[PD692X0_MAX_MANAGERS])
  666. {
  667. struct device_node *managers_node, *node;
  668. int ret, nmanagers, i, j;
  669. if (!priv->np)
  670. return -EINVAL;
  671. nmanagers = 0;
  672. managers_node = of_get_child_by_name(priv->np, "managers");
  673. if (!managers_node)
  674. return -EINVAL;
  675. for_each_child_of_node(managers_node, node) {
  676. u32 manager_id;
  677. if (!of_node_name_eq(node, "manager"))
  678. continue;
  679. ret = of_property_read_u32(node, "reg", &manager_id);
  680. if (ret)
  681. goto out;
  682. if (manager_id >= PD692X0_MAX_MANAGERS ||
  683. manager_id != nmanagers) {
  684. dev_err(&priv->client->dev,
  685. "wrong number or order of managers (%d)\n",
  686. manager_id);
  687. ret = -EINVAL;
  688. goto out;
  689. }
  690. ret = pd692x0_of_get_ports_manager(priv, &manager[manager_id],
  691. node);
  692. if (ret)
  693. goto out;
  694. nmanagers++;
  695. }
  696. of_node_put(managers_node);
  697. return nmanagers;
  698. out:
  699. for (i = 0; i < nmanagers; i++) {
  700. for (j = 0; j < manager[i].nports; j++) {
  701. of_node_put(manager[i].port_node[j]);
  702. manager[i].port_node[j] = NULL;
  703. }
  704. }
  705. of_node_put(node);
  706. of_node_put(managers_node);
  707. return ret;
  708. }
  709. static int
  710. pd692x0_set_port_matrix(const struct pse_pi_pairset *pairset,
  711. const struct pd692x0_manager *manager,
  712. int nmanagers, struct pd692x0_matrix *port_matrix)
  713. {
  714. int i, j, port_cnt;
  715. bool found = false;
  716. if (!pairset->np)
  717. return 0;
  718. /* Look on every managers */
  719. port_cnt = 0;
  720. for (i = 0; i < nmanagers; i++) {
  721. /* Look on every ports of the manager */
  722. for (j = 0; j < manager[i].nports; j++) {
  723. if (pairset->np == manager[i].port_node[j]) {
  724. found = true;
  725. break;
  726. }
  727. }
  728. port_cnt += j;
  729. if (found)
  730. break;
  731. }
  732. if (!found)
  733. return -ENODEV;
  734. if (pairset->pinout == ALTERNATIVE_A)
  735. port_matrix->hw_port_a = port_cnt;
  736. else if (pairset->pinout == ALTERNATIVE_B)
  737. port_matrix->hw_port_b = port_cnt;
  738. return 0;
  739. }
  740. static int
  741. pd692x0_set_ports_matrix(struct pd692x0_priv *priv,
  742. const struct pd692x0_manager *manager,
  743. int nmanagers,
  744. struct pd692x0_matrix port_matrix[PD692X0_MAX_PIS])
  745. {
  746. struct pse_controller_dev *pcdev = &priv->pcdev;
  747. int i, ret;
  748. /* Init Matrix */
  749. for (i = 0; i < PD692X0_MAX_PIS; i++) {
  750. port_matrix[i].hw_port_a = 0xff;
  751. port_matrix[i].hw_port_b = 0xff;
  752. }
  753. /* Update with values for every PSE PIs */
  754. for (i = 0; i < pcdev->nr_lines; i++) {
  755. ret = pd692x0_set_port_matrix(&pcdev->pi[i].pairset[0],
  756. manager, nmanagers,
  757. &port_matrix[i]);
  758. if (ret) {
  759. dev_err(&priv->client->dev,
  760. "unable to configure pi %d pairset 0", i);
  761. return ret;
  762. }
  763. ret = pd692x0_set_port_matrix(&pcdev->pi[i].pairset[1],
  764. manager, nmanagers,
  765. &port_matrix[i]);
  766. if (ret) {
  767. dev_err(&priv->client->dev,
  768. "unable to configure pi %d pairset 1", i);
  769. return ret;
  770. }
  771. }
  772. return 0;
  773. }
  774. static int
  775. pd692x0_write_ports_matrix(struct pd692x0_priv *priv,
  776. const struct pd692x0_matrix port_matrix[PD692X0_MAX_PIS])
  777. {
  778. struct pd692x0_msg msg, buf;
  779. int ret, i;
  780. /* Write temporary Matrix */
  781. msg = pd692x0_msg_template_list[PD692X0_MSG_SET_TMP_PORT_MATRIX];
  782. for (i = 0; i < PD692X0_MAX_PIS; i++) {
  783. msg.sub[2] = i;
  784. msg.data[0] = port_matrix[i].hw_port_b;
  785. msg.data[1] = port_matrix[i].hw_port_a;
  786. ret = pd692x0_sendrecv_msg(priv, &msg, &buf);
  787. if (ret < 0)
  788. return ret;
  789. }
  790. /* Program Matrix */
  791. msg = pd692x0_msg_template_list[PD692X0_MSG_PRG_PORT_MATRIX];
  792. ret = pd692x0_sendrecv_msg(priv, &msg, &buf);
  793. if (ret < 0)
  794. return ret;
  795. return 0;
  796. }
  797. static int pd692x0_setup_pi_matrix(struct pse_controller_dev *pcdev)
  798. {
  799. struct pd692x0_manager manager[PD692X0_MAX_MANAGERS] = {0};
  800. struct pd692x0_priv *priv = to_pd692x0_priv(pcdev);
  801. struct pd692x0_matrix port_matrix[PD692X0_MAX_PIS];
  802. int ret, i, j, nmanagers;
  803. /* Should we flash the port matrix */
  804. if (priv->fw_state != PD692X0_FW_OK &&
  805. priv->fw_state != PD692X0_FW_COMPLETE)
  806. return 0;
  807. ret = pd692x0_of_get_managers(priv, manager);
  808. if (ret < 0)
  809. return ret;
  810. nmanagers = ret;
  811. ret = pd692x0_set_ports_matrix(priv, manager, nmanagers, port_matrix);
  812. if (ret)
  813. goto out;
  814. ret = pd692x0_write_ports_matrix(priv, port_matrix);
  815. if (ret)
  816. goto out;
  817. out:
  818. for (i = 0; i < nmanagers; i++) {
  819. for (j = 0; j < manager[i].nports; j++)
  820. of_node_put(manager[i].port_node[j]);
  821. }
  822. return ret;
  823. }
  824. static int pd692x0_pi_get_voltage(struct pse_controller_dev *pcdev, int id)
  825. {
  826. struct pd692x0_priv *priv = to_pd692x0_priv(pcdev);
  827. struct pd692x0_msg msg, buf = {0};
  828. int ret;
  829. ret = pd692x0_fw_unavailable(priv);
  830. if (ret)
  831. return ret;
  832. msg = pd692x0_msg_template_list[PD692X0_MSG_GET_PORT_MEAS];
  833. msg.sub[2] = id;
  834. ret = pd692x0_sendrecv_msg(priv, &msg, &buf);
  835. if (ret < 0)
  836. return ret;
  837. /* Convert 0.1V unit to uV */
  838. return (buf.sub[0] << 8 | buf.sub[1]) * 100000;
  839. }
  840. static int pd692x0_pi_get_pw_limit(struct pse_controller_dev *pcdev,
  841. int id)
  842. {
  843. struct pd692x0_priv *priv = to_pd692x0_priv(pcdev);
  844. struct pd692x0_msg msg, buf = {0};
  845. int ret;
  846. msg = pd692x0_msg_template_list[PD692X0_MSG_GET_PORT_PARAM];
  847. msg.sub[2] = id;
  848. ret = pd692x0_sendrecv_msg(priv, &msg, &buf);
  849. if (ret < 0)
  850. return ret;
  851. return pd692x0_pi_get_pw_from_table(buf.data[0], buf.data[1]);
  852. }
  853. static int pd692x0_pi_set_pw_limit(struct pse_controller_dev *pcdev,
  854. int id, int max_mW)
  855. {
  856. struct pd692x0_priv *priv = to_pd692x0_priv(pcdev);
  857. struct device *dev = &priv->client->dev;
  858. struct pd692x0_msg msg, buf = {0};
  859. int ret;
  860. ret = pd692x0_fw_unavailable(priv);
  861. if (ret)
  862. return ret;
  863. msg = pd692x0_msg_template_list[PD692X0_MSG_SET_PORT_PARAM];
  864. msg.sub[2] = id;
  865. ret = pd692x0_pi_set_pw_from_table(dev, &msg, max_mW);
  866. if (ret)
  867. return ret;
  868. return pd692x0_sendrecv_msg(priv, &msg, &buf);
  869. }
  870. static const struct pse_controller_ops pd692x0_ops = {
  871. .setup_pi_matrix = pd692x0_setup_pi_matrix,
  872. .ethtool_get_status = pd692x0_ethtool_get_status,
  873. .pi_enable = pd692x0_pi_enable,
  874. .pi_disable = pd692x0_pi_disable,
  875. .pi_is_enabled = pd692x0_pi_is_enabled,
  876. .pi_get_voltage = pd692x0_pi_get_voltage,
  877. .pi_get_pw_limit = pd692x0_pi_get_pw_limit,
  878. .pi_set_pw_limit = pd692x0_pi_set_pw_limit,
  879. };
  880. #define PD692X0_FW_LINE_MAX_SZ 0xff
  881. static int pd692x0_fw_get_next_line(const u8 *data,
  882. char *line, size_t size)
  883. {
  884. size_t line_size;
  885. int i;
  886. line_size = min_t(size_t, size, PD692X0_FW_LINE_MAX_SZ);
  887. memset(line, 0, PD692X0_FW_LINE_MAX_SZ);
  888. for (i = 0; i < line_size - 1; i++) {
  889. if (*data == '\r' && *(data + 1) == '\n') {
  890. line[i] = '\r';
  891. line[i + 1] = '\n';
  892. return i + 2;
  893. }
  894. line[i] = *data;
  895. data++;
  896. }
  897. return -EIO;
  898. }
  899. static enum fw_upload_err
  900. pd692x0_fw_recv_resp(const struct i2c_client *client, unsigned long ms_timeout,
  901. const char *msg_ok, unsigned int msg_size)
  902. {
  903. /* Maximum controller response size */
  904. char fw_msg_buf[5] = {0};
  905. unsigned long timeout;
  906. int ret;
  907. if (msg_size > sizeof(fw_msg_buf))
  908. return FW_UPLOAD_ERR_RW_ERROR;
  909. /* Read until we get something */
  910. timeout = msecs_to_jiffies(ms_timeout) + jiffies;
  911. while (true) {
  912. if (time_is_before_jiffies(timeout))
  913. return FW_UPLOAD_ERR_TIMEOUT;
  914. ret = i2c_master_recv(client, fw_msg_buf, 1);
  915. if (ret < 0 || *fw_msg_buf == 0) {
  916. usleep_range(1000, 2000);
  917. continue;
  918. } else {
  919. break;
  920. }
  921. }
  922. /* Read remaining characters */
  923. ret = i2c_master_recv(client, fw_msg_buf + 1, msg_size - 1);
  924. if (strncmp(fw_msg_buf, msg_ok, msg_size)) {
  925. dev_err(&client->dev,
  926. "Wrong FW download process answer (%*pE)\n",
  927. msg_size, fw_msg_buf);
  928. return FW_UPLOAD_ERR_HW_ERROR;
  929. }
  930. return FW_UPLOAD_ERR_NONE;
  931. }
  932. static int pd692x0_fw_write_line(const struct i2c_client *client,
  933. const char line[PD692X0_FW_LINE_MAX_SZ],
  934. const bool last_line)
  935. {
  936. int ret;
  937. while (*line != 0) {
  938. ret = i2c_master_send(client, line, 1);
  939. if (ret < 0)
  940. return FW_UPLOAD_ERR_RW_ERROR;
  941. line++;
  942. }
  943. if (last_line) {
  944. ret = pd692x0_fw_recv_resp(client, 100, "TP\r\n",
  945. sizeof("TP\r\n") - 1);
  946. if (ret)
  947. return ret;
  948. } else {
  949. ret = pd692x0_fw_recv_resp(client, 100, "T*\r\n",
  950. sizeof("T*\r\n") - 1);
  951. if (ret)
  952. return ret;
  953. }
  954. return FW_UPLOAD_ERR_NONE;
  955. }
  956. static enum fw_upload_err pd692x0_fw_reset(const struct i2c_client *client)
  957. {
  958. const struct pd692x0_msg zero = {0};
  959. struct pd692x0_msg buf = {0};
  960. unsigned long timeout;
  961. char cmd[] = "RST";
  962. int ret;
  963. ret = i2c_master_send(client, cmd, strlen(cmd));
  964. if (ret < 0) {
  965. dev_err(&client->dev,
  966. "Failed to reset the controller (%pe)\n",
  967. ERR_PTR(ret));
  968. return ret;
  969. }
  970. timeout = msecs_to_jiffies(10000) + jiffies;
  971. while (true) {
  972. if (time_is_before_jiffies(timeout))
  973. return FW_UPLOAD_ERR_TIMEOUT;
  974. ret = i2c_master_recv(client, (u8 *)&buf, sizeof(buf));
  975. if (ret < 0 ||
  976. !memcmp(&buf, &zero, sizeof(buf)))
  977. usleep_range(1000, 2000);
  978. else
  979. break;
  980. }
  981. /* Is the reply a successful report message */
  982. if (buf.key != PD692X0_KEY_TLM || buf.echo != 0xff ||
  983. buf.sub[0] & 0x01) {
  984. dev_err(&client->dev, "PSE controller error\n");
  985. return FW_UPLOAD_ERR_HW_ERROR;
  986. }
  987. /* Is the firmware operational */
  988. if (buf.sub[0] & 0x02) {
  989. dev_err(&client->dev,
  990. "PSE firmware error. Please update it.\n");
  991. return FW_UPLOAD_ERR_HW_ERROR;
  992. }
  993. return FW_UPLOAD_ERR_NONE;
  994. }
  995. static enum fw_upload_err pd692x0_fw_prepare(struct fw_upload *fwl,
  996. const u8 *data, u32 size)
  997. {
  998. struct pd692x0_priv *priv = fwl->dd_handle;
  999. const struct i2c_client *client = priv->client;
  1000. enum pd692x0_fw_state last_fw_state;
  1001. int ret;
  1002. priv->cancel_request = false;
  1003. last_fw_state = priv->fw_state;
  1004. priv->fw_state = PD692X0_FW_PREPARE;
  1005. /* Enter program mode */
  1006. if (last_fw_state == PD692X0_FW_BROKEN) {
  1007. const char *msg = "ENTR";
  1008. const char *c;
  1009. c = msg;
  1010. do {
  1011. ret = i2c_master_send(client, c, 1);
  1012. if (ret < 0)
  1013. return FW_UPLOAD_ERR_RW_ERROR;
  1014. if (*(c + 1))
  1015. usleep_range(10000, 20000);
  1016. } while (*(++c));
  1017. } else {
  1018. struct pd692x0_msg msg, buf;
  1019. msg = pd692x0_msg_template_list[PD692X0_MSG_DOWNLOAD_CMD];
  1020. ret = pd692x0_sendrecv_msg(priv, &msg, &buf);
  1021. if (ret < 0) {
  1022. dev_err(&client->dev,
  1023. "Failed to enter programming mode (%pe)\n",
  1024. ERR_PTR(ret));
  1025. return FW_UPLOAD_ERR_RW_ERROR;
  1026. }
  1027. }
  1028. ret = pd692x0_fw_recv_resp(client, 100, "TPE\r\n", sizeof("TPE\r\n") - 1);
  1029. if (ret)
  1030. goto err_out;
  1031. if (priv->cancel_request) {
  1032. ret = FW_UPLOAD_ERR_CANCELED;
  1033. goto err_out;
  1034. }
  1035. return FW_UPLOAD_ERR_NONE;
  1036. err_out:
  1037. pd692x0_fw_reset(priv->client);
  1038. priv->fw_state = last_fw_state;
  1039. return ret;
  1040. }
  1041. static enum fw_upload_err pd692x0_fw_write(struct fw_upload *fwl,
  1042. const u8 *data, u32 offset,
  1043. u32 size, u32 *written)
  1044. {
  1045. struct pd692x0_priv *priv = fwl->dd_handle;
  1046. char line[PD692X0_FW_LINE_MAX_SZ];
  1047. const struct i2c_client *client;
  1048. int ret, i;
  1049. char cmd;
  1050. client = priv->client;
  1051. priv->fw_state = PD692X0_FW_WRITE;
  1052. /* Erase */
  1053. cmd = 'E';
  1054. ret = i2c_master_send(client, &cmd, 1);
  1055. if (ret < 0) {
  1056. dev_err(&client->dev,
  1057. "Failed to boot programming mode (%pe)\n",
  1058. ERR_PTR(ret));
  1059. return FW_UPLOAD_ERR_RW_ERROR;
  1060. }
  1061. ret = pd692x0_fw_recv_resp(client, 100, "TOE\r\n", sizeof("TOE\r\n") - 1);
  1062. if (ret)
  1063. return ret;
  1064. ret = pd692x0_fw_recv_resp(client, 5000, "TE\r\n", sizeof("TE\r\n") - 1);
  1065. if (ret)
  1066. dev_warn(&client->dev,
  1067. "Failed to erase internal memory, however still try to write Firmware\n");
  1068. ret = pd692x0_fw_recv_resp(client, 100, "TPE\r\n", sizeof("TPE\r\n") - 1);
  1069. if (ret)
  1070. dev_warn(&client->dev,
  1071. "Failed to erase internal memory, however still try to write Firmware\n");
  1072. if (priv->cancel_request)
  1073. return FW_UPLOAD_ERR_CANCELED;
  1074. /* Program */
  1075. cmd = 'P';
  1076. ret = i2c_master_send(client, &cmd, sizeof(char));
  1077. if (ret < 0) {
  1078. dev_err(&client->dev,
  1079. "Failed to boot programming mode (%pe)\n",
  1080. ERR_PTR(ret));
  1081. return ret;
  1082. }
  1083. ret = pd692x0_fw_recv_resp(client, 100, "TOP\r\n", sizeof("TOP\r\n") - 1);
  1084. if (ret)
  1085. return ret;
  1086. i = 0;
  1087. while (i < size) {
  1088. ret = pd692x0_fw_get_next_line(data, line, size - i);
  1089. if (ret < 0) {
  1090. ret = FW_UPLOAD_ERR_FW_INVALID;
  1091. goto err;
  1092. }
  1093. i += ret;
  1094. data += ret;
  1095. if (line[0] == 'S' && line[1] == '0') {
  1096. continue;
  1097. } else if (line[0] == 'S' && line[1] == '7') {
  1098. ret = pd692x0_fw_write_line(client, line, true);
  1099. if (ret)
  1100. goto err;
  1101. } else {
  1102. ret = pd692x0_fw_write_line(client, line, false);
  1103. if (ret)
  1104. goto err;
  1105. }
  1106. if (priv->cancel_request) {
  1107. ret = FW_UPLOAD_ERR_CANCELED;
  1108. goto err;
  1109. }
  1110. }
  1111. *written = i;
  1112. msleep(400);
  1113. return FW_UPLOAD_ERR_NONE;
  1114. err:
  1115. strscpy_pad(line, "S7\r\n", sizeof(line));
  1116. pd692x0_fw_write_line(client, line, true);
  1117. return ret;
  1118. }
  1119. static enum fw_upload_err pd692x0_fw_poll_complete(struct fw_upload *fwl)
  1120. {
  1121. struct pd692x0_priv *priv = fwl->dd_handle;
  1122. const struct i2c_client *client = priv->client;
  1123. struct pd692x0_msg_ver ver;
  1124. int ret;
  1125. priv->fw_state = PD692X0_FW_COMPLETE;
  1126. ret = pd692x0_fw_reset(client);
  1127. if (ret)
  1128. return ret;
  1129. ver = pd692x0_get_sw_version(priv);
  1130. if (ver.maj_sw_ver < PD692X0_FW_MAJ_VER) {
  1131. dev_err(&client->dev,
  1132. "Too old firmware version. Please update it\n");
  1133. priv->fw_state = PD692X0_FW_NEED_UPDATE;
  1134. return FW_UPLOAD_ERR_FW_INVALID;
  1135. }
  1136. ret = pd692x0_setup_pi_matrix(&priv->pcdev);
  1137. if (ret < 0) {
  1138. dev_err(&client->dev, "Error configuring ports matrix (%pe)\n",
  1139. ERR_PTR(ret));
  1140. priv->fw_state = PD692X0_FW_NEED_UPDATE;
  1141. return FW_UPLOAD_ERR_HW_ERROR;
  1142. }
  1143. priv->fw_state = PD692X0_FW_OK;
  1144. return FW_UPLOAD_ERR_NONE;
  1145. }
  1146. static void pd692x0_fw_cancel(struct fw_upload *fwl)
  1147. {
  1148. struct pd692x0_priv *priv = fwl->dd_handle;
  1149. priv->cancel_request = true;
  1150. }
  1151. static void pd692x0_fw_cleanup(struct fw_upload *fwl)
  1152. {
  1153. struct pd692x0_priv *priv = fwl->dd_handle;
  1154. switch (priv->fw_state) {
  1155. case PD692X0_FW_WRITE:
  1156. pd692x0_fw_reset(priv->client);
  1157. fallthrough;
  1158. case PD692X0_FW_COMPLETE:
  1159. priv->fw_state = PD692X0_FW_BROKEN;
  1160. break;
  1161. default:
  1162. break;
  1163. }
  1164. }
  1165. static const struct fw_upload_ops pd692x0_fw_ops = {
  1166. .prepare = pd692x0_fw_prepare,
  1167. .write = pd692x0_fw_write,
  1168. .poll_complete = pd692x0_fw_poll_complete,
  1169. .cancel = pd692x0_fw_cancel,
  1170. .cleanup = pd692x0_fw_cleanup,
  1171. };
  1172. static int pd692x0_i2c_probe(struct i2c_client *client)
  1173. {
  1174. struct pd692x0_msg msg, buf = {0}, zero = {0};
  1175. struct device *dev = &client->dev;
  1176. struct pd692x0_msg_ver ver;
  1177. struct pd692x0_priv *priv;
  1178. struct fw_upload *fwl;
  1179. int ret;
  1180. if (!i2c_check_functionality(client->adapter, I2C_FUNC_I2C)) {
  1181. dev_err(dev, "i2c check functionality failed\n");
  1182. return -ENXIO;
  1183. }
  1184. priv = devm_kzalloc(dev, sizeof(*priv), GFP_KERNEL);
  1185. if (!priv)
  1186. return -ENOMEM;
  1187. priv->client = client;
  1188. i2c_set_clientdata(client, priv);
  1189. ret = i2c_master_recv(client, (u8 *)&buf, sizeof(buf));
  1190. if (ret != sizeof(buf)) {
  1191. dev_err(dev, "Failed to get device status\n");
  1192. return -EIO;
  1193. }
  1194. /* Probe has been already run and the status dumped */
  1195. if (!memcmp(&buf, &zero, sizeof(buf))) {
  1196. /* Ask again the controller status */
  1197. msg = pd692x0_msg_template_list[PD692X0_MSG_GET_SYS_STATUS];
  1198. ret = pd692x0_sendrecv_msg(priv, &msg, &buf);
  1199. if (ret < 0) {
  1200. dev_err(dev, "Failed to get device status\n");
  1201. return ret;
  1202. }
  1203. }
  1204. if (buf.key != 0x03 || buf.sub[0] & 0x01) {
  1205. dev_err(dev, "PSE controller error\n");
  1206. return -EIO;
  1207. }
  1208. if (buf.sub[0] & 0x02) {
  1209. dev_err(dev, "PSE firmware error. Please update it.\n");
  1210. priv->fw_state = PD692X0_FW_BROKEN;
  1211. } else {
  1212. ver = pd692x0_get_sw_version(priv);
  1213. dev_info(&client->dev, "Software version %d.%02d.%d.%d\n",
  1214. ver.prod, ver.maj_sw_ver, ver.min_sw_ver,
  1215. ver.pa_sw_ver);
  1216. if (ver.maj_sw_ver < PD692X0_FW_MAJ_VER) {
  1217. dev_err(dev, "Too old firmware version. Please update it\n");
  1218. priv->fw_state = PD692X0_FW_NEED_UPDATE;
  1219. } else {
  1220. priv->fw_state = PD692X0_FW_OK;
  1221. }
  1222. }
  1223. priv->np = dev->of_node;
  1224. priv->pcdev.nr_lines = PD692X0_MAX_PIS;
  1225. priv->pcdev.owner = THIS_MODULE;
  1226. priv->pcdev.ops = &pd692x0_ops;
  1227. priv->pcdev.dev = dev;
  1228. priv->pcdev.types = ETHTOOL_PSE_C33;
  1229. ret = devm_pse_controller_register(dev, &priv->pcdev);
  1230. if (ret)
  1231. return dev_err_probe(dev, ret,
  1232. "failed to register PSE controller\n");
  1233. fwl = firmware_upload_register(THIS_MODULE, dev, dev_name(dev),
  1234. &pd692x0_fw_ops, priv);
  1235. if (IS_ERR(fwl))
  1236. return dev_err_probe(dev, PTR_ERR(fwl),
  1237. "failed to register to the Firmware Upload API\n");
  1238. priv->fwl = fwl;
  1239. return 0;
  1240. }
  1241. static void pd692x0_i2c_remove(struct i2c_client *client)
  1242. {
  1243. struct pd692x0_priv *priv = i2c_get_clientdata(client);
  1244. firmware_upload_unregister(priv->fwl);
  1245. }
  1246. static const struct i2c_device_id pd692x0_id[] = {
  1247. { PD692X0_PSE_NAME },
  1248. { }
  1249. };
  1250. MODULE_DEVICE_TABLE(i2c, pd692x0_id);
  1251. static const struct of_device_id pd692x0_of_match[] = {
  1252. { .compatible = "microchip,pd69200", },
  1253. { .compatible = "microchip,pd69210", },
  1254. { .compatible = "microchip,pd69220", },
  1255. { },
  1256. };
  1257. MODULE_DEVICE_TABLE(of, pd692x0_of_match);
  1258. static struct i2c_driver pd692x0_driver = {
  1259. .probe = pd692x0_i2c_probe,
  1260. .remove = pd692x0_i2c_remove,
  1261. .id_table = pd692x0_id,
  1262. .driver = {
  1263. .name = PD692X0_PSE_NAME,
  1264. .of_match_table = pd692x0_of_match,
  1265. },
  1266. };
  1267. module_i2c_driver(pd692x0_driver);
  1268. MODULE_AUTHOR("Kory Maincent <kory.maincent@bootlin.com>");
  1269. MODULE_DESCRIPTION("Microchip PD692x0 PoE PSE Controller driver");
  1270. MODULE_LICENSE("GPL");