spss_utils.c 34 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394959697989910010110210310410510610710810911011111211311411511611711811912012112212312412512612712812913013113213313413513613713813914014114214314414514614714814915015115215315415515615715815916016116216316416516616716816917017117217317417517617717817918018118218318418518618718818919019119219319419519619719819920020120220320420520620720820921021121221321421521621721821922022122222322422522622722822923023123223323423523623723823924024124224324424524624724824925025125225325425525625725825926026126226326426526626726826927027127227327427527627727827928028128228328428528628728828929029129229329429529629729829930030130230330430530630730830931031131231331431531631731831932032132232332432532632732832933033133233333433533633733833934034134234334434534634734834935035135235335435535635735835936036136236336436536636736836937037137237337437537637737837938038138238338438538638738838939039139239339439539639739839940040140240340440540640740840941041141241341441541641741841942042142242342442542642742842943043143243343443543643743843944044144244344444544644744844945045145245345445545645745845946046146246346446546646746846947047147247347447547647747847948048148248348448548648748848949049149249349449549649749849950050150250350450550650750850951051151251351451551651751851952052152252352452552652752852953053153253353453553653753853954054154254354454554654754854955055155255355455555655755855956056156256356456556656756856957057157257357457557657757857958058158258358458558658758858959059159259359459559659759859960060160260360460560660760860961061161261361461561661761861962062162262362462562662762862963063163263363463563663763863964064164264364464564664764864965065165265365465565665765865966066166266366466566666766866967067167267367467567667767867968068168268368468568668768868969069169269369469569669769869970070170270370470570670770870971071171271371471571671771871972072172272372472572672772872973073173273373473573673773873974074174274374474574674774874975075175275375475575675775875976076176276376476576676776876977077177277377477577677777877978078178278378478578678778878979079179279379479579679779879980080180280380480580680780880981081181281381481581681781881982082182282382482582682782882983083183283383483583683783883984084184284384484584684784884985085185285385485585685785885986086186286386486586686786886987087187287387487587687787887988088188288388488588688788888989089189289389489589689789889990090190290390490590690790890991091191291391491591691791891992092192292392492592692792892993093193293393493593693793893994094194294394494594694794894995095195295395495595695795895996096196296396496596696796896997097197297397497597697797897998098198298398498598698798898999099199299399499599699799899910001001100210031004100510061007100810091010101110121013101410151016101710181019102010211022102310241025102610271028102910301031103210331034103510361037103810391040104110421043104410451046104710481049105010511052105310541055105610571058105910601061106210631064106510661067106810691070107110721073107410751076107710781079108010811082108310841085108610871088108910901091109210931094109510961097109810991100110111021103110411051106110711081109111011111112111311141115111611171118111911201121112211231124112511261127112811291130113111321133113411351136113711381139114011411142114311441145114611471148114911501151115211531154115511561157115811591160116111621163116411651166116711681169117011711172117311741175117611771178117911801181118211831184118511861187118811891190119111921193119411951196119711981199120012011202120312041205120612071208120912101211121212131214121512161217121812191220122112221223122412251226122712281229123012311232123312341235123612371238123912401241124212431244124512461247124812491250125112521253125412551256125712581259126012611262126312641265126612671268126912701271127212731274127512761277127812791280128112821283128412851286128712881289129012911292129312941295129612971298129913001301130213031304130513061307130813091310131113121313131413151316131713181319132013211322132313241325132613271328132913301331133213331334133513361337133813391340134113421343134413451346
  1. // SPDX-License-Identifier: GPL-2.0-only
  2. /*
  3. * Copyright (c) 2016-2021, The Linux Foundation. All rights reserved.
  4. * Copyright (c) 2022 Qualcomm Innovation Center, Inc. All rights reserved.
  5. */
  6. /*
  7. * Secure-Processor-SubSystem (SPSS) utilities.
  8. *
  9. * This driver provides utilities for the Secure Processor (SP).
  10. *
  11. * The SP daemon needs to load different SPSS images based on:
  12. *
  13. * 1. Test/Production key used to sign the SPSS image (read fuses).
  14. * 2. SPSS HW version (selected via Device Tree).
  15. *
  16. */
  17. #define pr_fmt(fmt) "spss_utils [%s]: " fmt, __func__
  18. #include <linux/kernel.h> /* min() */
  19. #include <linux/module.h> /* MODULE_LICENSE */
  20. #include <linux/device.h> /* class_create() */
  21. #include <linux/slab.h> /* kzalloc() */
  22. #include <linux/fs.h> /* file_operations */
  23. #include <linux/cdev.h> /* cdev_add() */
  24. #include <linux/errno.h> /* EINVAL, ETIMEDOUT */
  25. #include <linux/printk.h> /* pr_err() */
  26. #include <linux/bitops.h> /* BIT(x) */
  27. #include <linux/platform_device.h> /* platform_driver_register() */
  28. #include <linux/of.h> /* of_property_count_strings() */
  29. #include <linux/of_address.h> /* of_address_to_resource() */
  30. #include <linux/io.h> /* ioremap() */
  31. #include <linux/notifier.h>
  32. #include <linux/sizes.h> /* SZ_4K */
  33. #include <linux/uaccess.h> /* copy_from_user() */
  34. #include <linux/completion.h> /* wait_for_completion_timeout() */
  35. #include <linux/reboot.h> /* kernel_restart() */
  36. #include <linux/remoteproc.h>
  37. #include <linux/remoteproc/qcom_rproc.h>
  38. #include <linux/remoteproc/qcom_spss.h>
  39. #include <soc/qcom/secure_buffer.h> /* VMID_HLOS */
  40. #include <uapi/linux/ioctl.h> /* ioctl() */
  41. #include <linux/spss_utils.h> /* IOCTL to user space */
  42. /* driver name */
  43. #define DEVICE_NAME "spss_utils"
  44. enum spss_firmware_type {
  45. SPSS_FW_TYPE_DEV = 'd',
  46. SPSS_FW_TYPE_TEST = 't',
  47. SPSS_FW_TYPE_PROD = 'p',
  48. SPSS_FW_TYPE_NONE = 'z',
  49. };
  50. static enum spss_firmware_type firmware_type = SPSS_FW_TYPE_TEST;
  51. static const char *dev_firmware_name;
  52. static const char *test_firmware_name;
  53. static const char *prod_firmware_name;
  54. static const char *none_firmware_name = "nospss";
  55. static const char *firmware_name = "NA";
  56. static struct device *spss_dev;
  57. /* SP_SCSR_MBn_SP2CL_GPm(n,m) */
  58. static u32 spss_debug_reg_addr; /*SP_SCSR_MB0_SP2CL_GP0*/
  59. static u32 spss_debug_reg_addr1; /*SP_SCSR_MB1_SP2CL_GP0*/
  60. static u32 spss_debug_reg_addr3; /*SP_SCSR_MB3_SP2CL_GP0*/
  61. static u32 spss_emul_type_reg_addr; /* TCSR_SOC_EMULATION_TYPE */
  62. static void *iar_notif_handle;
  63. static struct notifier_block *iar_nb;
  64. static bool is_iar_active;
  65. static bool is_ssr_disabled;
  66. #define CMAC_SIZE_IN_BYTES (128/8) /* 128 bit = 16 bytes */
  67. #define CMAC_SIZE_IN_DWORDS (CMAC_SIZE_IN_BYTES/sizeof(u32)) /* 4 dwords */
  68. // MCP code size register holds size divided by a factor
  69. // To get the actual size, need to multiply by the same factor
  70. #define MCP_SIZE_MUL_FACTOR (4)
  71. static u32 pil_addr;
  72. static u32 pil_size;
  73. /*
  74. * The saved fw cmac is stored in file in IAR-DB.
  75. * It is provided via ioctl from user space spu service.
  76. */
  77. static u32 saved_fw_cmac[CMAC_SIZE_IN_DWORDS]; /* saved fw cmac */
  78. /*
  79. * The calculated fw cmac is calculated by SPU PBL.
  80. * It is read from shared memory and provided back to user space service
  81. * via device attribute.
  82. */
  83. static u32 calc_fw_cmac[CMAC_SIZE_IN_DWORDS]; /* calculated pbl fw cmac */
  84. /*
  85. * The saved apps cmac is stored in file in IAR-DB.
  86. * It is provided via ioctl from user space spu service.
  87. */
  88. static u32 saved_apps_cmac[MAX_SPU_UEFI_APPS][CMAC_SIZE_IN_DWORDS];
  89. /*
  90. * The calculated apps cmac is calculated by SPU firmware.
  91. * It is read from shared memory and provided back to user space service
  92. * via device attribute.
  93. */
  94. static u32 calc_apps_cmac[MAX_SPU_UEFI_APPS][CMAC_SIZE_IN_DWORDS];
  95. static void __iomem *cmac_mem;
  96. static phys_addr_t cmac_mem_addr;
  97. #define CMAC_MEM_SIZE SZ_4K /* XPU align to 4KB */
  98. #define SPSS_BASE_ADDR_MASK 0xFFFF0000
  99. #define SPSS_RMB_CODE_SIZE_REG_OFFSET 0x1008
  100. #define SPU_EMULATUION (BIT(0) | BIT(1))
  101. #define SPU_PRESENT_IN_EMULATION BIT(0)
  102. /* IOCTL max request size is 1KB */
  103. #define MAX_IOCTL_REQ_SIZE 1024
  104. /* Events notification */
  105. static struct completion spss_events[SPSS_NUM_EVENTS];
  106. static bool spss_events_signaled[SPSS_NUM_EVENTS];
  107. /* Protect from ioctl signal func called by multiple-proc at the same time */
  108. static struct mutex event_lock;
  109. /**
  110. * struct device state
  111. */
  112. struct spss_utils_device {
  113. /* char device info */
  114. struct cdev *cdev;
  115. dev_t device_no;
  116. struct class *driver_class;
  117. struct device *class_dev;
  118. struct platform_device *pdev;
  119. };
  120. /* Device State */
  121. static struct spss_utils_device *spss_utils_dev;
  122. /* static functions declaration */
  123. static int spss_set_saved_fw_cmac(u32 *cmac, size_t cmac_size);
  124. static int spss_set_saved_uefi_apps_cmac(void);
  125. static int spss_get_fw_calc_cmac(void);
  126. static int spss_get_apps_calc_cmac(void);
  127. /*==========================================================================*/
  128. /* Device Sysfs */
  129. /*==========================================================================*/
  130. static ssize_t firmware_name_show(struct device *dev,
  131. struct device_attribute *attr,
  132. char *buf)
  133. {
  134. int ret;
  135. if (!dev || !attr || !buf) {
  136. pr_err("invalid param.\n");
  137. return -EINVAL;
  138. }
  139. if (firmware_name == NULL)
  140. ret = scnprintf(buf, PAGE_SIZE, "%s\n", "unknown");
  141. else
  142. ret = scnprintf(buf, PAGE_SIZE, "%s\n", firmware_name);
  143. return ret;
  144. }
  145. static DEVICE_ATTR_RO(firmware_name);
  146. static ssize_t test_fuse_state_show(struct device *dev,
  147. struct device_attribute *attr,
  148. char *buf)
  149. {
  150. int ret;
  151. if (!dev || !attr || !buf) {
  152. pr_err("invalid param.\n");
  153. return -EINVAL;
  154. }
  155. switch (firmware_type) {
  156. case SPSS_FW_TYPE_DEV:
  157. ret = scnprintf(buf, PAGE_SIZE, "%s", "dev");
  158. break;
  159. case SPSS_FW_TYPE_TEST:
  160. ret = scnprintf(buf, PAGE_SIZE, "%s", "test");
  161. break;
  162. case SPSS_FW_TYPE_PROD:
  163. ret = scnprintf(buf, PAGE_SIZE, "%s", "prod");
  164. break;
  165. default:
  166. return -EINVAL;
  167. }
  168. return ret;
  169. }
  170. static DEVICE_ATTR_RO(test_fuse_state);
  171. static ssize_t spss_debug_reg_show(struct device *dev,
  172. struct device_attribute *attr,
  173. char *buf)
  174. {
  175. int ret = 0;
  176. void __iomem *spss_debug_reg = NULL;
  177. void __iomem *spss_debug_reg1 = NULL;
  178. void __iomem *spss_debug_reg3 = NULL;
  179. u32 val1, val2, val3, val4, val7, val8;
  180. if (!dev || !attr || !buf) {
  181. pr_err("invalid param.\n");
  182. return -EINVAL;
  183. }
  184. pr_debug("spss_debug_reg_addr [0x%x].\n", spss_debug_reg_addr);
  185. pr_debug("spss_debug_reg_addr1 [0x%x].\n", spss_debug_reg_addr1);
  186. pr_debug("spss_debug_reg_addr3 [0x%x].\n", spss_debug_reg_addr3);
  187. spss_debug_reg = ioremap(spss_debug_reg_addr, sizeof(u32)*2);
  188. spss_debug_reg1 = ioremap(spss_debug_reg_addr1, sizeof(u32)*2);
  189. spss_debug_reg3 = ioremap(spss_debug_reg_addr3, sizeof(u32)*2);
  190. if (!spss_debug_reg) {
  191. pr_err("can't map SPSS debug reg addr\n");
  192. goto unmap_reg;
  193. }
  194. if (!spss_debug_reg1) {
  195. pr_err("can't map SPSS debug reg addr1\n");
  196. goto unmap_reg1;
  197. }
  198. if (!spss_debug_reg3) {
  199. pr_err("can't map SPSS debug reg addr3\n");
  200. goto unmap_reg3;
  201. }
  202. val1 = readl_relaxed(spss_debug_reg);
  203. val2 = readl_relaxed(((char *) spss_debug_reg) + sizeof(u32));
  204. val3 = readl_relaxed(spss_debug_reg1);
  205. val4 = readl_relaxed(((char *) spss_debug_reg1) + sizeof(u32));
  206. val7 = readl_relaxed(spss_debug_reg3);
  207. val8 = readl_relaxed(((char *) spss_debug_reg3) + sizeof(u32));
  208. ret = scnprintf(buf, PAGE_SIZE,
  209. "MB0: val1[0x%x] val2[0x%x],\n MB1: val3[0x%x] val4[0x%x],\n MB3: val7[0x%x] val8[0x%x]\n",
  210. val1, val2, val3, val4, val7, val8);
  211. unmap_reg3:
  212. iounmap(spss_debug_reg3);
  213. unmap_reg1:
  214. iounmap(spss_debug_reg1);
  215. unmap_reg:
  216. iounmap(spss_debug_reg);
  217. return ret;
  218. }
  219. static DEVICE_ATTR_RO(spss_debug_reg);
  220. static ssize_t calc_fw_cmac_show(struct device *dev,
  221. struct device_attribute *attr,
  222. char *buf)
  223. {
  224. if (!dev || !attr || !buf) {
  225. pr_err("invalid param.\n");
  226. return -EINVAL;
  227. }
  228. /* first make sure the calc cmac is updated */
  229. spss_get_fw_calc_cmac();
  230. memcpy(buf, calc_fw_cmac, sizeof(calc_fw_cmac));
  231. return sizeof(calc_fw_cmac);
  232. }
  233. static DEVICE_ATTR_RO(calc_fw_cmac);
  234. static ssize_t calc_apps_cmac_show(struct device *dev,
  235. struct device_attribute *attr, char *buf)
  236. {
  237. if (!dev || !attr || !buf) {
  238. pr_err("invalid param.\n");
  239. return -EINVAL;
  240. }
  241. /* first make sure the calc cmac is updated */
  242. spss_get_apps_calc_cmac();
  243. memcpy(buf, calc_apps_cmac, sizeof(calc_apps_cmac));
  244. return sizeof(calc_apps_cmac);
  245. }
  246. static DEVICE_ATTR_RO(calc_apps_cmac);
  247. /*--------------------------------------------------------------------------*/
  248. static int spss_create_sysfs(struct device *dev)
  249. {
  250. int ret;
  251. ret = device_create_file(dev, &dev_attr_firmware_name);
  252. if (ret < 0) {
  253. pr_err("failed to create sysfs file for firmware_name.\n");
  254. return ret;
  255. }
  256. ret = device_create_file(dev, &dev_attr_test_fuse_state);
  257. if (ret < 0) {
  258. pr_err("failed to create sysfs file for test_fuse_state.\n");
  259. goto remove_firmware_name;
  260. }
  261. ret = device_create_file(dev, &dev_attr_spss_debug_reg);
  262. if (ret < 0) {
  263. pr_err("failed to create sysfs file for spss_debug_reg.\n");
  264. goto remove_test_fuse_state;
  265. }
  266. ret = device_create_file(dev, &dev_attr_calc_fw_cmac);
  267. if (ret < 0) {
  268. pr_err("failed to create sysfs file for calc_fw_cmac.\n");
  269. goto remove_spss_debug_reg;
  270. }
  271. ret = device_create_file(dev, &dev_attr_calc_apps_cmac);
  272. if (ret < 0) {
  273. pr_err("failed to create sysfs file for calc_apps_cmac.\n");
  274. goto remove_calc_fw_cmac;
  275. }
  276. return 0;
  277. remove_calc_fw_cmac:
  278. device_remove_file(dev, &dev_attr_calc_fw_cmac);
  279. remove_spss_debug_reg:
  280. device_remove_file(dev, &dev_attr_spss_debug_reg);
  281. remove_test_fuse_state:
  282. device_remove_file(dev, &dev_attr_test_fuse_state);
  283. remove_firmware_name:
  284. device_remove_file(dev, &dev_attr_firmware_name);
  285. return ret;
  286. }
  287. static void spss_destroy_sysfs(struct device *dev)
  288. {
  289. device_remove_file(dev, &dev_attr_calc_apps_cmac);
  290. device_remove_file(dev, &dev_attr_calc_fw_cmac);
  291. device_remove_file(dev, &dev_attr_spss_debug_reg);
  292. device_remove_file(dev, &dev_attr_test_fuse_state);
  293. device_remove_file(dev, &dev_attr_firmware_name);
  294. }
  295. /*==========================================================================*/
  296. /* IOCTL */
  297. /*==========================================================================*/
  298. static int spss_wait_for_event(struct spss_ioc_wait_for_event *req)
  299. {
  300. int ret;
  301. uint32_t event_id;
  302. uint32_t timeout_sec;
  303. long timeleft = 1;
  304. event_id = req->event_id;
  305. timeout_sec = req->timeout_sec;
  306. if (event_id >= SPSS_NUM_EVENTS) {
  307. pr_err("event_id [%d] invalid\n", event_id);
  308. return -EINVAL;
  309. }
  310. pr_debug("wait for event [%d], timeout_sec [%d]\n",
  311. event_id, timeout_sec);
  312. if (timeout_sec) {
  313. unsigned long jiffies = 0;
  314. jiffies = msecs_to_jiffies(timeout_sec*1000);
  315. timeleft = wait_for_completion_interruptible_timeout(
  316. &spss_events[event_id], jiffies);
  317. ret = timeleft;
  318. } else {
  319. ret = wait_for_completion_interruptible(
  320. &spss_events[event_id]);
  321. }
  322. if (timeleft == 0) {
  323. pr_err("wait for event [%d] timeout [%d] sec expired\n",
  324. event_id, timeout_sec);
  325. req->status = EVENT_STATUS_TIMEOUT;
  326. } else if (ret < 0) {
  327. pr_err("wait for event [%d] interrupted. ret [%d]\n",
  328. event_id, ret);
  329. req->status = EVENT_STATUS_ABORTED;
  330. if (ret == -ERESTARTSYS) /* handle LPM event */
  331. return ret;
  332. } else {
  333. pr_debug("wait for event [%d] completed.\n", event_id);
  334. req->status = EVENT_STATUS_SIGNALED;
  335. }
  336. return 0;
  337. }
  338. static int spss_signal_event(struct spss_ioc_signal_event *req)
  339. {
  340. uint32_t event_id;
  341. mutex_lock(&event_lock);
  342. event_id = req->event_id;
  343. if (event_id >= SPSS_NUM_EVENTS) {
  344. pr_err("event_id [%d] invalid\n", event_id);
  345. mutex_unlock(&event_lock);
  346. return -EINVAL;
  347. }
  348. if (spss_events_signaled[event_id]) {
  349. pr_err("event_id [%d] already signaled\n", event_id);
  350. mutex_unlock(&event_lock);
  351. return -EINVAL;
  352. }
  353. pr_debug("signal event [%d]\n", event_id);
  354. complete_all(&spss_events[event_id]);
  355. req->status = EVENT_STATUS_SIGNALED;
  356. spss_events_signaled[event_id] = true;
  357. mutex_unlock(&event_lock);
  358. return 0;
  359. }
  360. static int spss_is_event_signaled(struct spss_ioc_is_signaled *req)
  361. {
  362. uint32_t event_id;
  363. mutex_lock(&event_lock);
  364. event_id = req->event_id;
  365. if (event_id >= SPSS_NUM_EVENTS) {
  366. pr_err("event_id [%d] invalid\n", event_id);
  367. mutex_unlock(&event_lock);
  368. return -EINVAL;
  369. }
  370. if (spss_events_signaled[event_id])
  371. req->status = EVENT_STATUS_SIGNALED;
  372. else
  373. req->status = EVENT_STATUS_NOT_SIGNALED;
  374. mutex_unlock(&event_lock);
  375. return 0;
  376. }
  377. static int spss_handle_set_fw_and_apps_cmac(struct spss_ioc_set_fw_and_apps_cmac *req)
  378. {
  379. int ret = 0;
  380. u32 cmac_buf_size = req->cmac_buf_size;
  381. void __user *cmac_buf_ptr = u64_to_user_ptr(req->cmac_buf_ptr);
  382. u32 num_of_cmacs = req->num_of_cmacs;
  383. /* Saved cmacs of spu firmware and UEFI loaded spu apps */
  384. u32 fw_and_apps_cmacs[1+MAX_SPU_UEFI_APPS][CMAC_SIZE_IN_DWORDS];
  385. pr_debug("cmac_buf_size [0x%x].\n", (int) req->cmac_buf_size);
  386. pr_debug("cmac_buf_ptr [0x%x].\n", (int) req->cmac_buf_ptr);
  387. pr_debug("num_of_cmacs [0x%x].\n", (int) req->num_of_cmacs);
  388. if (cmac_buf_size != sizeof(fw_and_apps_cmacs)) {
  389. pr_err("cmac_buf_size [0x%x] invalid.\n", cmac_buf_size);
  390. return -EINVAL;
  391. }
  392. if (num_of_cmacs > (u32)(MAX_SPU_UEFI_APPS+1)) {
  393. pr_err("num_of_cmacs [0x%x] invalid.\n", num_of_cmacs);
  394. return -EINVAL;
  395. }
  396. /* copy the saved cmacs from user buffer to loacl variable */
  397. ret = copy_from_user(fw_and_apps_cmacs, cmac_buf_ptr, cmac_buf_size);
  398. if (ret < 0) {
  399. pr_err("copy_from_user() from cmac_buf_ptr failed.\n");
  400. return -EFAULT;
  401. }
  402. /* store the saved fw cmac */
  403. memcpy(saved_fw_cmac, fw_and_apps_cmacs[0],
  404. sizeof(saved_fw_cmac));
  405. pr_debug("saved fw cmac: 0x%08x,0x%08x,0x%08x,0x%08x\n",
  406. saved_fw_cmac[0], saved_fw_cmac[1],
  407. saved_fw_cmac[2], saved_fw_cmac[3]);
  408. /* store the saved apps cmac */
  409. memcpy(saved_apps_cmac, &fw_and_apps_cmacs[1][0],
  410. sizeof(saved_apps_cmac));
  411. /*
  412. * SPSS is loaded now by UEFI,
  413. * so PIL-IAR-callback is not being called on power-up by PIL.
  414. * therefore get the saved spu fw cmac and apps cmac from ioctl.
  415. * The PIL-IAR-callback shall be called on spss SSR.
  416. * The saved cmacs are used on QCOM_SSR_AFTER_POWERUP event !
  417. */
  418. spss_set_saved_fw_cmac(saved_fw_cmac, sizeof(saved_fw_cmac));
  419. spss_set_saved_uefi_apps_cmac();
  420. pr_debug("completed ok\n");
  421. return 0;
  422. }
  423. static long spss_utils_ioctl(struct file *file,
  424. unsigned int cmd, unsigned long arg)
  425. {
  426. int ret;
  427. void *buf = (void *) arg;
  428. uint8_t data[MAX_IOCTL_REQ_SIZE] = {0};
  429. size_t size = 0;
  430. void *req = (void *) data;
  431. if (buf == NULL) {
  432. pr_err("invalid ioctl arg\n");
  433. return -EINVAL;
  434. }
  435. size = _IOC_SIZE(cmd);
  436. if (size && (cmd & IOC_IN)) {
  437. if (size > sizeof(data)) {
  438. pr_err("cmd [0x%x] size [0x%x] too large\n",
  439. cmd, size);
  440. return -EINVAL;
  441. }
  442. if (copy_from_user(data, (void __user *)arg, size)) {
  443. pr_err("copy_from_user() failed, cmd [0x%x] size [0x%x]\n",
  444. cmd, size);
  445. return -EFAULT;
  446. }
  447. }
  448. switch (cmd) {
  449. case SPSS_IOC_SET_FW_AND_APPS_CMAC:
  450. pr_debug("ioctl [SPSS_IOC_SET_FW_AND_APPS_CMAC]\n");
  451. /* spdaemon uses this ioctl only when IAR is active */
  452. is_iar_active = true;
  453. if (cmac_mem == NULL) {
  454. cmac_mem = ioremap(cmac_mem_addr, CMAC_MEM_SIZE);
  455. if (!cmac_mem) {
  456. pr_err("can't map cmac_mem.\n");
  457. return -EFAULT;
  458. }
  459. }
  460. ret = spss_handle_set_fw_and_apps_cmac(req);
  461. if (ret < 0)
  462. return ret;
  463. break;
  464. case SPSS_IOC_WAIT_FOR_EVENT:
  465. /* check input params */
  466. if (size != sizeof(struct spss_ioc_wait_for_event)) {
  467. pr_err("cmd [0x%x] invalid size [0x%x]\n", cmd, size);
  468. return -EINVAL;
  469. }
  470. ret = spss_wait_for_event(req);
  471. if (ret < 0)
  472. return ret;
  473. ret = copy_to_user((void __user *)arg, data, size);
  474. if (ret) {
  475. pr_err("cmd [0x%x] copy_to_user failed - %d\n", cmd, ret);
  476. return ret;
  477. }
  478. break;
  479. case SPSS_IOC_SIGNAL_EVENT:
  480. /* check input params */
  481. if (size != sizeof(struct spss_ioc_signal_event)) {
  482. pr_err("cmd [0x%x] invalid size [0x%x]\n", cmd, size);
  483. return -EINVAL;
  484. }
  485. ret = spss_signal_event(req);
  486. if (ret < 0)
  487. return ret;
  488. ret = copy_to_user((void __user *)arg, data, size);
  489. if (ret) {
  490. pr_err("cmd [0x%x] copy_to_user failed - %d\n", cmd, ret);
  491. return ret;
  492. }
  493. break;
  494. case SPSS_IOC_IS_EVENT_SIGNALED:
  495. /* check input params */
  496. if (size != sizeof(struct spss_ioc_is_signaled)) {
  497. pr_err("cmd [0x%x] invalid size [0x%x]\n", cmd, size);
  498. return -EINVAL;
  499. }
  500. ret = spss_is_event_signaled(req);
  501. if (ret < 0)
  502. return ret;
  503. ret = copy_to_user((void __user *)arg, data, size);
  504. if (ret) {
  505. pr_err("cmd [0x%x] copy_to_user failed - %d\n", cmd, ret);
  506. return ret;
  507. }
  508. break;
  509. case SPSS_IOC_SET_SSR_STATE:
  510. /* check input params */
  511. if (size != sizeof(uint32_t)) {
  512. pr_err("cmd [0x%x] invalid size [0x%x]\n", cmd, size);
  513. return -EINVAL;
  514. }
  515. if (is_iar_active) {
  516. uint32_t tmp = 0;
  517. memcpy(&tmp, data, sizeof(tmp));
  518. is_ssr_disabled = (bool) tmp; /* u32 to bool */
  519. pr_info("SSR disabled state updated to: %d\n",
  520. is_ssr_disabled);
  521. }
  522. pr_info("is_iar_active [%d] is_ssr_disabled [%d].\n",
  523. is_iar_active, is_ssr_disabled);
  524. break;
  525. default:
  526. pr_err("invalid ioctl cmd [0x%x]\n", cmd);
  527. return -ENOIOCTLCMD;
  528. }
  529. return 0;
  530. }
  531. static const struct file_operations spss_utils_fops = {
  532. .owner = THIS_MODULE,
  533. .unlocked_ioctl = spss_utils_ioctl,
  534. .compat_ioctl = spss_utils_ioctl,
  535. };
  536. static int spss_utils_create_chardev(struct device *dev)
  537. {
  538. int ret;
  539. unsigned int baseminor = 0;
  540. unsigned int count = 1;
  541. void *priv = (void *) spss_utils_dev;
  542. spss_utils_dev->cdev =
  543. kzalloc(sizeof(*spss_utils_dev->cdev), GFP_KERNEL);
  544. if (!spss_utils_dev->cdev)
  545. return -ENOMEM;
  546. /* get device_no */
  547. ret = alloc_chrdev_region(&spss_utils_dev->device_no, baseminor, count,
  548. DEVICE_NAME);
  549. if (ret < 0) {
  550. pr_err("alloc_chrdev_region failed %d\n", ret);
  551. return ret;
  552. }
  553. spss_utils_dev->driver_class = class_create(THIS_MODULE, DEVICE_NAME);
  554. if (IS_ERR(spss_utils_dev->driver_class)) {
  555. ret = -ENOMEM;
  556. pr_err("class_create failed %d\n", ret);
  557. goto exit_unreg_chrdev_region;
  558. }
  559. spss_utils_dev->class_dev =
  560. device_create(spss_utils_dev->driver_class, NULL,
  561. spss_utils_dev->device_no, priv,
  562. DEVICE_NAME);
  563. if (IS_ERR(spss_utils_dev->class_dev)) {
  564. pr_err("class_device_create failed %d\n", ret);
  565. ret = -ENOMEM;
  566. goto exit_destroy_class;
  567. }
  568. cdev_init(spss_utils_dev->cdev, &spss_utils_fops);
  569. spss_utils_dev->cdev->owner = THIS_MODULE;
  570. ret = cdev_add(spss_utils_dev->cdev,
  571. MKDEV(MAJOR(spss_utils_dev->device_no), 0),
  572. 1);
  573. if (ret < 0) {
  574. pr_err("cdev_add failed %d\n", ret);
  575. goto exit_destroy_device;
  576. }
  577. pr_debug("char device created.\n");
  578. return 0;
  579. exit_destroy_device:
  580. device_destroy(spss_utils_dev->driver_class, spss_utils_dev->device_no);
  581. exit_destroy_class:
  582. class_destroy(spss_utils_dev->driver_class);
  583. exit_unreg_chrdev_region:
  584. unregister_chrdev_region(spss_utils_dev->device_no, 1);
  585. return ret;
  586. }
  587. static void spss_utils_destroy_chardev(void)
  588. {
  589. device_destroy(spss_utils_dev->driver_class, spss_utils_dev->device_no);
  590. class_destroy(spss_utils_dev->driver_class);
  591. unregister_chrdev_region(spss_utils_dev->device_no, 1);
  592. }
  593. /*==========================================================================*/
  594. /* Device Tree */
  595. /*==========================================================================*/
  596. /* get the ACTUAL spss PIL firmware size from spu reg */
  597. static int get_pil_size(phys_addr_t base_addr)
  598. {
  599. u32 spss_code_size_addr = 0;
  600. void __iomem *spss_code_size_reg = NULL;
  601. u32 pil_size = 0;
  602. spss_code_size_addr = base_addr + SPSS_RMB_CODE_SIZE_REG_OFFSET;
  603. spss_code_size_reg = ioremap(spss_code_size_addr, sizeof(u32));
  604. if (!spss_code_size_reg) {
  605. pr_err("can't map spss_code_size_addr\n");
  606. return -EINVAL;
  607. }
  608. pil_size = readl_relaxed(spss_code_size_reg);
  609. iounmap(spss_code_size_reg);
  610. // Multiply the value read from code size register by factor
  611. // to get the actual size (see MCP_SIZE_MUL_FACTOR documentation)
  612. pil_size *= MCP_SIZE_MUL_FACTOR;
  613. if (pil_size % SZ_4K) {
  614. pr_err("pil_size [0x%08x] is not 4K aligned.\n", pil_size);
  615. return -EFAULT;
  616. }
  617. return pil_size;
  618. }
  619. /**
  620. * spss_parse_dt() - Parse Device Tree info.
  621. */
  622. static int spss_parse_dt(struct device_node *node)
  623. {
  624. int ret;
  625. u32 spss_fuse1_addr = 0;
  626. u32 spss_fuse1_bit = 0;
  627. u32 spss_fuse1_mask = 0;
  628. void __iomem *spss_fuse1_reg = NULL;
  629. u32 spss_fuse2_addr = 0;
  630. u32 spss_fuse2_bit = 0;
  631. u32 spss_fuse2_mask = 0;
  632. void __iomem *spss_fuse2_reg = NULL;
  633. struct device_node *np;
  634. struct resource r;
  635. u32 val1 = 0;
  636. u32 val2 = 0;
  637. void __iomem *spss_emul_type_reg = NULL;
  638. u32 spss_emul_type_val = 0;
  639. phys_addr_t spss_regs_base_addr = 0;
  640. ret = of_property_read_string(node, "qcom,spss-dev-firmware-name",
  641. &dev_firmware_name);
  642. if (ret < 0) {
  643. pr_err("can't get dev fw name\n");
  644. return -EINVAL;
  645. }
  646. ret = of_property_read_string(node, "qcom,spss-test-firmware-name",
  647. &test_firmware_name);
  648. if (ret < 0) {
  649. pr_err("can't get test fw name\n");
  650. return -EINVAL;
  651. }
  652. ret = of_property_read_string(node, "qcom,spss-prod-firmware-name",
  653. &prod_firmware_name);
  654. if (ret < 0) {
  655. pr_err("can't get prod fw name\n");
  656. return -EINVAL;
  657. }
  658. ret = of_property_read_u32(node, "qcom,spss-fuse1-addr",
  659. &spss_fuse1_addr);
  660. if (ret < 0) {
  661. pr_err("can't get fuse1 addr\n");
  662. return -EINVAL;
  663. }
  664. ret = of_property_read_u32(node, "qcom,spss-fuse2-addr",
  665. &spss_fuse2_addr);
  666. if (ret < 0) {
  667. pr_err("can't get fuse2 addr\n");
  668. return -EINVAL;
  669. }
  670. ret = of_property_read_u32(node, "qcom,spss-fuse1-bit",
  671. &spss_fuse1_bit);
  672. if (ret < 0) {
  673. pr_err("can't get fuse1 bit\n");
  674. return -EINVAL;
  675. }
  676. ret = of_property_read_u32(node, "qcom,spss-fuse2-bit",
  677. &spss_fuse2_bit);
  678. if (ret < 0) {
  679. pr_err("can't get fuse2 bit\n");
  680. return -EINVAL;
  681. }
  682. spss_fuse1_mask = BIT(spss_fuse1_bit);
  683. spss_fuse2_mask = BIT(spss_fuse2_bit);
  684. pr_debug("spss fuse1 addr [0x%x] bit [%d]\n",
  685. (int) spss_fuse1_addr, (int) spss_fuse1_bit);
  686. pr_debug("spss fuse2 addr [0x%x] bit [%d]\n",
  687. (int) spss_fuse2_addr, (int) spss_fuse2_bit);
  688. spss_fuse1_reg = ioremap(spss_fuse1_addr, sizeof(u32));
  689. if (!spss_fuse1_reg) {
  690. pr_err("can't map fuse1 addr\n");
  691. return -EINVAL;
  692. }
  693. spss_fuse2_reg = ioremap(spss_fuse2_addr, sizeof(u32));
  694. if (!spss_fuse2_reg) {
  695. iounmap(spss_fuse1_reg);
  696. pr_err("can't map fuse2 addr\n");
  697. return -EINVAL;
  698. }
  699. val1 = readl_relaxed(spss_fuse1_reg);
  700. val2 = readl_relaxed(spss_fuse2_reg);
  701. pr_debug("spss fuse1 value [0x%08x]\n", (int) val1);
  702. pr_debug("spss fuse2 value [0x%08x]\n", (int) val2);
  703. pr_debug("spss fuse1 mask [0x%08x]\n", (int) spss_fuse1_mask);
  704. pr_debug("spss fuse2 mask [0x%08x]\n", (int) spss_fuse2_mask);
  705. /**
  706. * Set firmware_type based on fuses:
  707. * SPSS_CONFIG_MODE 11: prod, changed from DEV to PROD due to
  708. PTE configuration error in Waipio 2.1 CONFIG_MODE 11 will be used
  709. for production signed MCP as workaround.
  710. * SPSS_CONFIG_MODE 01 or 10: test
  711. * SPSS_CONFIG_MODE 00: prod
  712. */
  713. if ((val1 & spss_fuse1_mask) && (val2 & spss_fuse2_mask))
  714. firmware_type = SPSS_FW_TYPE_PROD;
  715. else if ((val1 & spss_fuse1_mask) || (val2 & spss_fuse2_mask))
  716. firmware_type = SPSS_FW_TYPE_TEST;
  717. else
  718. firmware_type = SPSS_FW_TYPE_PROD;
  719. iounmap(spss_fuse1_reg);
  720. iounmap(spss_fuse2_reg);
  721. pr_debug("firmware_type value [%c]\n", firmware_type);
  722. ret = of_property_read_u32(node, "qcom,spss-debug-reg-addr",
  723. &spss_debug_reg_addr);
  724. if (ret < 0) {
  725. pr_err("can't get debug regs addr\n");
  726. return ret;
  727. }
  728. ret = of_property_read_u32(node, "qcom,spss-debug-reg-addr1",
  729. &spss_debug_reg_addr1);
  730. if (ret < 0) {
  731. pr_err("can't get debug regs addr1\n");
  732. return ret;
  733. }
  734. ret = of_property_read_u32(node, "qcom,spss-debug-reg-addr3",
  735. &spss_debug_reg_addr3);
  736. if (ret < 0) {
  737. pr_err("can't get debug regs addr3\n");
  738. return ret;
  739. }
  740. ret = of_property_read_u32(node, "qcom,spss-emul-type-reg-addr",
  741. &spss_emul_type_reg_addr);
  742. if (ret < 0) {
  743. pr_err("can't get spss-emulation-type-reg addr\n");
  744. return -EINVAL;
  745. }
  746. spss_emul_type_reg = ioremap(spss_emul_type_reg_addr,
  747. sizeof(u32));
  748. if (!spss_emul_type_reg) {
  749. pr_err("can't map soc-emulation-type reg addr\n");
  750. return -EINVAL;
  751. }
  752. spss_emul_type_val = readl_relaxed(spss_emul_type_reg);
  753. pr_debug("spss_emul_type value [0x%08x]\n", (int)spss_emul_type_val);
  754. if (spss_emul_type_val & SPU_EMULATUION) {
  755. if (spss_emul_type_val & SPU_PRESENT_IN_EMULATION) {
  756. firmware_type = SPSS_FW_TYPE_TEST;
  757. } else {
  758. /* for some emulation platforms SPSS is not present */
  759. firmware_type = SPSS_FW_TYPE_NONE;
  760. }
  761. pr_debug("remap firmware_type value [%c]\n", firmware_type);
  762. }
  763. iounmap(spss_emul_type_reg);
  764. /* PIL-SPSS area */
  765. np = of_parse_phandle(node, "pil-mem", 0);
  766. if (!np) {
  767. pr_err("no pil-mem entry, check pil-addr\n");
  768. ret = of_property_read_u32(node, "qcom,pil-addr",
  769. &pil_addr);
  770. if (ret < 0) {
  771. pr_err("can't get pil_addr\n");
  772. return -EFAULT;
  773. }
  774. } else {
  775. ret = of_address_to_resource(np, 0, &r);
  776. of_node_put(np);
  777. if (ret)
  778. return ret;
  779. pil_addr = (u32)r.start;
  780. }
  781. spss_regs_base_addr =
  782. (spss_debug_reg_addr & SPSS_BASE_ADDR_MASK);
  783. ret = get_pil_size(spss_regs_base_addr);
  784. if (ret < 0) {
  785. pr_err("failed to get pil_size.\n");
  786. return -EFAULT;
  787. }
  788. pil_size = (u32) ret;
  789. pr_debug("pil_addr [0x%08x].\n", pil_addr);
  790. pr_debug("pil_size [0x%08x].\n", pil_size);
  791. /* cmac buffer after spss firmware end */
  792. cmac_mem_addr = pil_addr + pil_size;
  793. pr_info("iar_buf_addr [0x%08x].\n", cmac_mem_addr);
  794. memset(saved_fw_cmac, 0xA5, sizeof(saved_fw_cmac));
  795. memset(saved_apps_cmac, 0xA5, sizeof(saved_apps_cmac));
  796. return 0;
  797. }
  798. static int spss_set_saved_fw_cmac(u32 *cmac, size_t cmac_size)
  799. {
  800. u8 __iomem *reg = NULL;
  801. int i;
  802. if (cmac_mem == NULL) {
  803. pr_err("invalid cmac_mem.\n");
  804. return -EFAULT;
  805. }
  806. reg = cmac_mem;
  807. for (i = 0; i < cmac_size/sizeof(u32); i++)
  808. writel_relaxed(cmac[i], reg + i*sizeof(u32));
  809. pr_debug("saved fw cmac: 0x%08x,0x%08x,0x%08x,0x%08x\n",
  810. cmac[0], cmac[1], cmac[2], cmac[3]);
  811. return 0;
  812. }
  813. static int spss_get_fw_calc_cmac(void)
  814. {
  815. u8 __iomem *reg = NULL;
  816. int i;
  817. u32 val;
  818. u32 cmac[CMAC_SIZE_IN_DWORDS] = {0};
  819. if (cmac_mem == NULL) {
  820. pr_err("invalid cmac_mem.\n");
  821. return -EFAULT;
  822. }
  823. reg = cmac_mem; /* IAR buffer base */
  824. reg += CMAC_SIZE_IN_BYTES; /* skip the saved cmac */
  825. memset(calc_fw_cmac, 0, sizeof(calc_fw_cmac));
  826. /* get pbl fw cmac from ddr */
  827. for (i = 0; i < CMAC_SIZE_IN_DWORDS; i++) {
  828. val = readl_relaxed(reg);
  829. calc_fw_cmac[i] = val;
  830. reg += sizeof(u32);
  831. }
  832. /* check for any pattern to mark invalid cmac */
  833. if (cmac[0] == cmac[1])
  834. return -EINVAL; /* not valid cmac */
  835. memcpy(calc_fw_cmac, cmac, sizeof(calc_fw_cmac));
  836. pr_debug("calc_fw_cmac : 0x%08x,0x%08x,0x%08x,0x%08x\n",
  837. calc_fw_cmac[0], calc_fw_cmac[1],
  838. calc_fw_cmac[2], calc_fw_cmac[3]);
  839. return 0;
  840. }
  841. static int spss_get_apps_calc_cmac(void)
  842. {
  843. u8 __iomem *reg = NULL;
  844. int i, j;
  845. u32 val;
  846. if (cmac_mem == NULL) {
  847. pr_err("invalid cmac_mem.\n");
  848. return -EFAULT;
  849. }
  850. reg = cmac_mem; /* IAR buffer base */
  851. reg += CMAC_SIZE_IN_BYTES; /* skip the saved fw cmac */
  852. reg += CMAC_SIZE_IN_BYTES; /* skip the calc fw cmac */
  853. reg += CMAC_SIZE_IN_BYTES; /* skip the saved 1st app cmac */
  854. memset(calc_apps_cmac, 0, sizeof(calc_apps_cmac));
  855. /* get apps cmac from ddr */
  856. for (j = 0; j < ARRAY_SIZE(calc_apps_cmac); j++) {
  857. u32 cmac[CMAC_SIZE_IN_DWORDS] = {0};
  858. memset(cmac, 0, sizeof(cmac));
  859. for (i = 0; i < ARRAY_SIZE(cmac); i++) {
  860. val = readl_relaxed(reg);
  861. cmac[i] = val;
  862. reg += sizeof(u32);
  863. }
  864. reg += CMAC_SIZE_IN_BYTES; /* skip the saved cmac */
  865. /* check for any pattern to mark end of cmacs */
  866. if (cmac[0] == cmac[1])
  867. break; /* no more valid cmacs */
  868. memcpy(calc_apps_cmac[j], cmac, sizeof(calc_apps_cmac[j]));
  869. pr_debug("app [%d] cmac : 0x%08x,0x%08x,0x%08x,0x%08x\n", j,
  870. calc_apps_cmac[j][0], calc_apps_cmac[j][1],
  871. calc_apps_cmac[j][2], calc_apps_cmac[j][3]);
  872. }
  873. return 0;
  874. }
  875. static int spss_set_saved_uefi_apps_cmac(void)
  876. {
  877. u8 __iomem *reg = NULL;
  878. int i, j;
  879. u32 val;
  880. if (cmac_mem == NULL) {
  881. pr_err("invalid cmac_mem.\n");
  882. return -EFAULT;
  883. }
  884. reg = cmac_mem; /* IAR buffer base */
  885. reg += (2*CMAC_SIZE_IN_BYTES); /* skip the saved and calc fw cmac */
  886. /* get saved apps cmac from ddr - were written by UEFI spss driver */
  887. for (j = 0; j < MAX_SPU_UEFI_APPS; j++) {
  888. if (saved_apps_cmac[j][0] == saved_apps_cmac[j][1])
  889. break; /* no more cmacs */
  890. for (i = 0; i < CMAC_SIZE_IN_DWORDS; i++) {
  891. val = saved_apps_cmac[j][i];
  892. writel_relaxed(val, reg);
  893. reg += sizeof(u32);
  894. }
  895. reg += CMAC_SIZE_IN_BYTES; /* skip the calc app cmac */
  896. pr_debug("app[%d] saved cmac: 0x%08x,0x%08x,0x%08x,0x%08x\n",
  897. j,
  898. saved_apps_cmac[j][0], saved_apps_cmac[j][1],
  899. saved_apps_cmac[j][2], saved_apps_cmac[j][3]);
  900. }
  901. return 0;
  902. }
  903. static int spss_utils_rproc_callback(struct notifier_block *nb,
  904. unsigned long code,
  905. void *data)
  906. {
  907. int i, event_id;
  908. switch (code) {
  909. case QCOM_SSR_BEFORE_SHUTDOWN:
  910. pr_debug("[QCOM_SSR_BEFORE_SHUTDOWN] event.\n");
  911. mutex_lock(&event_lock);
  912. /* Reset NVM-ready and SPU-ready events */
  913. for (i = SPSS_EVENT_ID_NVM_READY;
  914. i <= SPSS_EVENT_ID_SPU_READY; i++) {
  915. reinit_completion(&spss_events[i]);
  916. spss_events_signaled[i] = false;
  917. }
  918. mutex_unlock(&event_lock);
  919. pr_debug("reset spss events.\n");
  920. break;
  921. case QCOM_SSR_AFTER_SHUTDOWN:
  922. pr_debug("[QCOM_SSR_AFTER_SHUTDOWN] event.\n");
  923. mutex_lock(&event_lock);
  924. event_id = SPSS_EVENT_ID_SPU_POWER_DOWN;
  925. complete_all(&spss_events[event_id]);
  926. spss_events_signaled[event_id] = true;
  927. event_id = SPSS_EVENT_ID_SPU_POWER_UP;
  928. reinit_completion(&spss_events[event_id]);
  929. spss_events_signaled[event_id] = false;
  930. mutex_unlock(&event_lock);
  931. break;
  932. case QCOM_SSR_BEFORE_POWERUP:
  933. pr_debug("[QCOM_SSR_BEFORE_POWERUP] event.\n");
  934. if (is_iar_active) {
  935. if (is_ssr_disabled) {
  936. pr_warn("SPSS SSR disabled, requesting reboot\n");
  937. kernel_restart("SPSS SSR disabled, requesting reboot");
  938. } else {
  939. /* Called on SSR as spss firmware is loaded by UEFI */
  940. spss_set_saved_fw_cmac(saved_fw_cmac, sizeof(saved_fw_cmac));
  941. spss_set_saved_uefi_apps_cmac();
  942. }
  943. }
  944. break;
  945. case QCOM_SSR_AFTER_POWERUP:
  946. pr_info("QCOM_SSR_AFTER_POWERUP] event.\n");
  947. mutex_lock(&event_lock);
  948. event_id = SPSS_EVENT_ID_SPU_POWER_UP;
  949. complete_all(&spss_events[event_id]);
  950. spss_events_signaled[event_id] = true;
  951. event_id = SPSS_EVENT_ID_SPU_POWER_DOWN;
  952. reinit_completion(&spss_events[event_id]);
  953. spss_events_signaled[event_id] = false;
  954. mutex_unlock(&event_lock);
  955. /*
  956. * For IAR-DB-Recovery, read cmac regadless of is_iar_active.
  957. * please notice that HYP unmap this area, it is a race.
  958. */
  959. if (cmac_mem == NULL) {
  960. cmac_mem = ioremap(cmac_mem_addr, CMAC_MEM_SIZE);
  961. if (!cmac_mem) {
  962. pr_err("can't map cmac_mem.\n");
  963. return -EFAULT;
  964. }
  965. }
  966. spss_get_fw_calc_cmac();
  967. spss_get_apps_calc_cmac();
  968. break;
  969. default:
  970. pr_err("unknown code [0x%x] .\n", (int) code);
  971. break;
  972. }
  973. return NOTIFY_OK;
  974. }
  975. /**
  976. * spss_probe() - initialization sequence
  977. */
  978. static int spss_probe(struct platform_device *pdev)
  979. {
  980. int ret = 0;
  981. int i;
  982. struct device_node *np = NULL;
  983. struct device *dev = &pdev->dev;
  984. struct property *prop = NULL;
  985. struct rproc *rproc = NULL;
  986. np = pdev->dev.of_node;
  987. spss_dev = dev;
  988. platform_set_drvdata(pdev, dev);
  989. ret = spss_parse_dt(np);
  990. if (ret < 0)
  991. return ret;
  992. switch (firmware_type) {
  993. case SPSS_FW_TYPE_DEV:
  994. firmware_name = dev_firmware_name;
  995. break;
  996. case SPSS_FW_TYPE_TEST:
  997. firmware_name = test_firmware_name;
  998. break;
  999. case SPSS_FW_TYPE_PROD:
  1000. firmware_name = prod_firmware_name;
  1001. break;
  1002. case SPSS_FW_TYPE_NONE:
  1003. firmware_name = none_firmware_name;
  1004. break;
  1005. default:
  1006. pr_err("invalid firmware type %d, sysfs entry not created\n",
  1007. firmware_type);
  1008. return -EINVAL;
  1009. }
  1010. prop = of_find_property(np, "qcom,rproc-handle", NULL);
  1011. if (!prop)
  1012. return -EINVAL;
  1013. rproc = rproc_get_by_phandle(be32_to_cpup(prop->value));
  1014. if (!rproc)
  1015. return -EPROBE_DEFER;
  1016. ret = qcom_spss_set_fw_name(rproc, firmware_name);
  1017. if (ret < 0) {
  1018. if (ret != -EINVAL)
  1019. pr_err("fail to set firmware name for remoteproc (%d)\n", ret);
  1020. return -EPROBE_DEFER;
  1021. }
  1022. rproc_put(rproc);
  1023. spss_utils_dev = kzalloc(sizeof(*spss_utils_dev), GFP_KERNEL);
  1024. if (spss_utils_dev == NULL)
  1025. return -ENOMEM;
  1026. ret = spss_utils_create_chardev(dev);
  1027. if (ret < 0)
  1028. return ret;
  1029. ret = spss_create_sysfs(dev);
  1030. if (ret < 0)
  1031. return ret;
  1032. iar_nb = kzalloc(sizeof(*iar_nb), GFP_KERNEL);
  1033. if (!iar_nb)
  1034. return -ENOMEM;
  1035. iar_nb->notifier_call = spss_utils_rproc_callback;
  1036. iar_notif_handle = qcom_register_ssr_notifier("spss", iar_nb);
  1037. if (IS_ERR_OR_NULL(iar_notif_handle)) {
  1038. pr_err("register fail for IAR notifier\n");
  1039. kfree(iar_nb);
  1040. iar_notif_handle = NULL;
  1041. iar_nb = NULL;
  1042. }
  1043. for (i = 0 ; i < SPSS_NUM_EVENTS; i++) {
  1044. init_completion(&spss_events[i]);
  1045. spss_events_signaled[i] = false;
  1046. }
  1047. mutex_init(&event_lock);
  1048. is_iar_active = false;
  1049. is_ssr_disabled = false;
  1050. pr_info("Probe completed successfully, [%s].\n", firmware_name);
  1051. return 0;
  1052. }
  1053. static int spss_remove(struct platform_device *pdev)
  1054. {
  1055. spss_utils_destroy_chardev();
  1056. spss_destroy_sysfs(spss_dev);
  1057. if (!iar_notif_handle && !iar_nb)
  1058. qcom_unregister_ssr_notifier(iar_notif_handle, iar_nb);
  1059. kfree(iar_nb);
  1060. iar_nb = 0;
  1061. kfree(spss_utils_dev);
  1062. spss_utils_dev = 0;
  1063. if (cmac_mem != NULL) {
  1064. iounmap(cmac_mem);
  1065. cmac_mem = NULL;
  1066. }
  1067. return 0;
  1068. }
  1069. static const struct of_device_id spss_match_table[] = {
  1070. { .compatible = "qcom,spss-utils", },
  1071. { },
  1072. };
  1073. static struct platform_driver spss_driver = {
  1074. .probe = spss_probe,
  1075. .remove = spss_remove,
  1076. .driver = {
  1077. .name = DEVICE_NAME,
  1078. .of_match_table = of_match_ptr(spss_match_table),
  1079. },
  1080. };
  1081. /*==========================================================================*/
  1082. /* Driver Init/Exit */
  1083. /*==========================================================================*/
  1084. static int __init spss_init(void)
  1085. {
  1086. int ret = 0;
  1087. ret = platform_driver_register(&spss_driver);
  1088. if (ret)
  1089. pr_err("register platform driver failed, ret [%d]\n", ret);
  1090. return ret;
  1091. }
  1092. late_initcall(spss_init); /* start after PIL driver */
  1093. static void __exit spss_exit(void)
  1094. {
  1095. platform_driver_unregister(&spss_driver);
  1096. }
  1097. module_exit(spss_exit)
  1098. MODULE_SOFTDEP("pre: qcom_spss");
  1099. MODULE_LICENSE("GPL v2");
  1100. MODULE_DESCRIPTION("Secure Processor Utilities");