]> git.karo-electronics.de Git - linux-beck.git/blob - drivers/firmware/qcom_scm-32.c
Merge tag 'for-linus-4.6-rc0-tag' of git://git.kernel.org/pub/scm/linux/kernel/git...
[linux-beck.git] / drivers / firmware / qcom_scm-32.c
1 /* Copyright (c) 2010,2015, The Linux Foundation. All rights reserved.
2  * Copyright (C) 2015 Linaro Ltd.
3  *
4  * This program is free software; you can redistribute it and/or modify
5  * it under the terms of the GNU General Public License version 2 and
6  * only version 2 as published by the Free Software Foundation.
7  *
8  * This program is distributed in the hope that it will be useful,
9  * but WITHOUT ANY WARRANTY; without even the implied warranty of
10  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
11  * GNU General Public License for more details.
12  *
13  * You should have received a copy of the GNU General Public License
14  * along with this program; if not, write to the Free Software
15  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
16  * 02110-1301, USA.
17  */
18
19 #include <linux/slab.h>
20 #include <linux/io.h>
21 #include <linux/module.h>
22 #include <linux/mutex.h>
23 #include <linux/errno.h>
24 #include <linux/err.h>
25 #include <linux/qcom_scm.h>
26
27 #include <asm/cacheflush.h>
28
29 #include "qcom_scm.h"
30
31 #define QCOM_SCM_FLAG_COLDBOOT_CPU0     0x00
32 #define QCOM_SCM_FLAG_COLDBOOT_CPU1     0x01
33 #define QCOM_SCM_FLAG_COLDBOOT_CPU2     0x08
34 #define QCOM_SCM_FLAG_COLDBOOT_CPU3     0x20
35
36 #define QCOM_SCM_FLAG_WARMBOOT_CPU0     0x04
37 #define QCOM_SCM_FLAG_WARMBOOT_CPU1     0x02
38 #define QCOM_SCM_FLAG_WARMBOOT_CPU2     0x10
39 #define QCOM_SCM_FLAG_WARMBOOT_CPU3     0x40
40
41 struct qcom_scm_entry {
42         int flag;
43         void *entry;
44 };
45
46 static struct qcom_scm_entry qcom_scm_wb[] = {
47         { .flag = QCOM_SCM_FLAG_WARMBOOT_CPU0 },
48         { .flag = QCOM_SCM_FLAG_WARMBOOT_CPU1 },
49         { .flag = QCOM_SCM_FLAG_WARMBOOT_CPU2 },
50         { .flag = QCOM_SCM_FLAG_WARMBOOT_CPU3 },
51 };
52
53 static DEFINE_MUTEX(qcom_scm_lock);
54
55 /**
56  * struct qcom_scm_command - one SCM command buffer
57  * @len: total available memory for command and response
58  * @buf_offset: start of command buffer
59  * @resp_hdr_offset: start of response buffer
60  * @id: command to be executed
61  * @buf: buffer returned from qcom_scm_get_command_buffer()
62  *
63  * An SCM command is laid out in memory as follows:
64  *
65  *      ------------------- <--- struct qcom_scm_command
66  *      | command header  |
67  *      ------------------- <--- qcom_scm_get_command_buffer()
68  *      | command buffer  |
69  *      ------------------- <--- struct qcom_scm_response and
70  *      | response header |      qcom_scm_command_to_response()
71  *      ------------------- <--- qcom_scm_get_response_buffer()
72  *      | response buffer |
73  *      -------------------
74  *
75  * There can be arbitrary padding between the headers and buffers so
76  * you should always use the appropriate qcom_scm_get_*_buffer() routines
77  * to access the buffers in a safe manner.
78  */
79 struct qcom_scm_command {
80         __le32 len;
81         __le32 buf_offset;
82         __le32 resp_hdr_offset;
83         __le32 id;
84         __le32 buf[0];
85 };
86
87 /**
88  * struct qcom_scm_response - one SCM response buffer
89  * @len: total available memory for response
90  * @buf_offset: start of response data relative to start of qcom_scm_response
91  * @is_complete: indicates if the command has finished processing
92  */
93 struct qcom_scm_response {
94         __le32 len;
95         __le32 buf_offset;
96         __le32 is_complete;
97 };
98
99 /**
100  * alloc_qcom_scm_command() - Allocate an SCM command
101  * @cmd_size: size of the command buffer
102  * @resp_size: size of the response buffer
103  *
104  * Allocate an SCM command, including enough room for the command
105  * and response headers as well as the command and response buffers.
106  *
107  * Returns a valid &qcom_scm_command on success or %NULL if the allocation fails.
108  */
109 static struct qcom_scm_command *alloc_qcom_scm_command(size_t cmd_size, size_t resp_size)
110 {
111         struct qcom_scm_command *cmd;
112         size_t len = sizeof(*cmd) + sizeof(struct qcom_scm_response) + cmd_size +
113                 resp_size;
114         u32 offset;
115
116         cmd = kzalloc(PAGE_ALIGN(len), GFP_KERNEL);
117         if (cmd) {
118                 cmd->len = cpu_to_le32(len);
119                 offset = offsetof(struct qcom_scm_command, buf);
120                 cmd->buf_offset = cpu_to_le32(offset);
121                 cmd->resp_hdr_offset = cpu_to_le32(offset + cmd_size);
122         }
123         return cmd;
124 }
125
126 /**
127  * free_qcom_scm_command() - Free an SCM command
128  * @cmd: command to free
129  *
130  * Free an SCM command.
131  */
132 static inline void free_qcom_scm_command(struct qcom_scm_command *cmd)
133 {
134         kfree(cmd);
135 }
136
137 /**
138  * qcom_scm_command_to_response() - Get a pointer to a qcom_scm_response
139  * @cmd: command
140  *
141  * Returns a pointer to a response for a command.
142  */
143 static inline struct qcom_scm_response *qcom_scm_command_to_response(
144                 const struct qcom_scm_command *cmd)
145 {
146         return (void *)cmd + le32_to_cpu(cmd->resp_hdr_offset);
147 }
148
149 /**
150  * qcom_scm_get_command_buffer() - Get a pointer to a command buffer
151  * @cmd: command
152  *
153  * Returns a pointer to the command buffer of a command.
154  */
155 static inline void *qcom_scm_get_command_buffer(const struct qcom_scm_command *cmd)
156 {
157         return (void *)cmd->buf;
158 }
159
160 /**
161  * qcom_scm_get_response_buffer() - Get a pointer to a response buffer
162  * @rsp: response
163  *
164  * Returns a pointer to a response buffer of a response.
165  */
166 static inline void *qcom_scm_get_response_buffer(const struct qcom_scm_response *rsp)
167 {
168         return (void *)rsp + le32_to_cpu(rsp->buf_offset);
169 }
170
171 static int qcom_scm_remap_error(int err)
172 {
173         pr_err("qcom_scm_call failed with error code %d\n", err);
174         switch (err) {
175         case QCOM_SCM_ERROR:
176                 return -EIO;
177         case QCOM_SCM_EINVAL_ADDR:
178         case QCOM_SCM_EINVAL_ARG:
179                 return -EINVAL;
180         case QCOM_SCM_EOPNOTSUPP:
181                 return -EOPNOTSUPP;
182         case QCOM_SCM_ENOMEM:
183                 return -ENOMEM;
184         }
185         return -EINVAL;
186 }
187
188 static u32 smc(u32 cmd_addr)
189 {
190         int context_id;
191         register u32 r0 asm("r0") = 1;
192         register u32 r1 asm("r1") = (u32)&context_id;
193         register u32 r2 asm("r2") = cmd_addr;
194         do {
195                 asm volatile(
196                         __asmeq("%0", "r0")
197                         __asmeq("%1", "r0")
198                         __asmeq("%2", "r1")
199                         __asmeq("%3", "r2")
200 #ifdef REQUIRES_SEC
201                         ".arch_extension sec\n"
202 #endif
203                         "smc    #0      @ switch to secure world\n"
204                         : "=r" (r0)
205                         : "r" (r0), "r" (r1), "r" (r2)
206                         : "r3");
207         } while (r0 == QCOM_SCM_INTERRUPTED);
208
209         return r0;
210 }
211
212 static int __qcom_scm_call(const struct qcom_scm_command *cmd)
213 {
214         int ret;
215         u32 cmd_addr = virt_to_phys(cmd);
216
217         /*
218          * Flush the command buffer so that the secure world sees
219          * the correct data.
220          */
221         secure_flush_area(cmd, cmd->len);
222
223         ret = smc(cmd_addr);
224         if (ret < 0)
225                 ret = qcom_scm_remap_error(ret);
226
227         return ret;
228 }
229
230 static void qcom_scm_inv_range(unsigned long start, unsigned long end)
231 {
232         u32 cacheline_size, ctr;
233
234         asm volatile("mrc p15, 0, %0, c0, c0, 1" : "=r" (ctr));
235         cacheline_size = 4 << ((ctr >> 16) & 0xf);
236
237         start = round_down(start, cacheline_size);
238         end = round_up(end, cacheline_size);
239         outer_inv_range(start, end);
240         while (start < end) {
241                 asm ("mcr p15, 0, %0, c7, c6, 1" : : "r" (start)
242                      : "memory");
243                 start += cacheline_size;
244         }
245         dsb();
246         isb();
247 }
248
249 /**
250  * qcom_scm_call() - Send an SCM command
251  * @svc_id: service identifier
252  * @cmd_id: command identifier
253  * @cmd_buf: command buffer
254  * @cmd_len: length of the command buffer
255  * @resp_buf: response buffer
256  * @resp_len: length of the response buffer
257  *
258  * Sends a command to the SCM and waits for the command to finish processing.
259  *
260  * A note on cache maintenance:
261  * Note that any buffers that are expected to be accessed by the secure world
262  * must be flushed before invoking qcom_scm_call and invalidated in the cache
263  * immediately after qcom_scm_call returns. Cache maintenance on the command
264  * and response buffers is taken care of by qcom_scm_call; however, callers are
265  * responsible for any other cached buffers passed over to the secure world.
266  */
267 static int qcom_scm_call(u32 svc_id, u32 cmd_id, const void *cmd_buf,
268                         size_t cmd_len, void *resp_buf, size_t resp_len)
269 {
270         int ret;
271         struct qcom_scm_command *cmd;
272         struct qcom_scm_response *rsp;
273         unsigned long start, end;
274
275         cmd = alloc_qcom_scm_command(cmd_len, resp_len);
276         if (!cmd)
277                 return -ENOMEM;
278
279         cmd->id = cpu_to_le32((svc_id << 10) | cmd_id);
280         if (cmd_buf)
281                 memcpy(qcom_scm_get_command_buffer(cmd), cmd_buf, cmd_len);
282
283         mutex_lock(&qcom_scm_lock);
284         ret = __qcom_scm_call(cmd);
285         mutex_unlock(&qcom_scm_lock);
286         if (ret)
287                 goto out;
288
289         rsp = qcom_scm_command_to_response(cmd);
290         start = (unsigned long)rsp;
291
292         do {
293                 qcom_scm_inv_range(start, start + sizeof(*rsp));
294         } while (!rsp->is_complete);
295
296         end = (unsigned long)qcom_scm_get_response_buffer(rsp) + resp_len;
297         qcom_scm_inv_range(start, end);
298
299         if (resp_buf)
300                 memcpy(resp_buf, qcom_scm_get_response_buffer(rsp), resp_len);
301 out:
302         free_qcom_scm_command(cmd);
303         return ret;
304 }
305
306 #define SCM_CLASS_REGISTER      (0x2 << 8)
307 #define SCM_MASK_IRQS           BIT(5)
308 #define SCM_ATOMIC(svc, cmd, n) (((((svc) << 10)|((cmd) & 0x3ff)) << 12) | \
309                                 SCM_CLASS_REGISTER | \
310                                 SCM_MASK_IRQS | \
311                                 (n & 0xf))
312
313 /**
314  * qcom_scm_call_atomic1() - Send an atomic SCM command with one argument
315  * @svc_id: service identifier
316  * @cmd_id: command identifier
317  * @arg1: first argument
318  *
319  * This shall only be used with commands that are guaranteed to be
320  * uninterruptable, atomic and SMP safe.
321  */
322 static s32 qcom_scm_call_atomic1(u32 svc, u32 cmd, u32 arg1)
323 {
324         int context_id;
325
326         register u32 r0 asm("r0") = SCM_ATOMIC(svc, cmd, 1);
327         register u32 r1 asm("r1") = (u32)&context_id;
328         register u32 r2 asm("r2") = arg1;
329
330         asm volatile(
331                         __asmeq("%0", "r0")
332                         __asmeq("%1", "r0")
333                         __asmeq("%2", "r1")
334                         __asmeq("%3", "r2")
335 #ifdef REQUIRES_SEC
336                         ".arch_extension sec\n"
337 #endif
338                         "smc    #0      @ switch to secure world\n"
339                         : "=r" (r0)
340                         : "r" (r0), "r" (r1), "r" (r2)
341                         : "r3");
342         return r0;
343 }
344
345 u32 qcom_scm_get_version(void)
346 {
347         int context_id;
348         static u32 version = -1;
349         register u32 r0 asm("r0");
350         register u32 r1 asm("r1");
351
352         if (version != -1)
353                 return version;
354
355         mutex_lock(&qcom_scm_lock);
356
357         r0 = 0x1 << 8;
358         r1 = (u32)&context_id;
359         do {
360                 asm volatile(
361                         __asmeq("%0", "r0")
362                         __asmeq("%1", "r1")
363                         __asmeq("%2", "r0")
364                         __asmeq("%3", "r1")
365 #ifdef REQUIRES_SEC
366                         ".arch_extension sec\n"
367 #endif
368                         "smc    #0      @ switch to secure world\n"
369                         : "=r" (r0), "=r" (r1)
370                         : "r" (r0), "r" (r1)
371                         : "r2", "r3");
372         } while (r0 == QCOM_SCM_INTERRUPTED);
373
374         version = r1;
375         mutex_unlock(&qcom_scm_lock);
376
377         return version;
378 }
379 EXPORT_SYMBOL(qcom_scm_get_version);
380
381 /*
382  * Set the cold/warm boot address for one of the CPU cores.
383  */
384 static int qcom_scm_set_boot_addr(u32 addr, int flags)
385 {
386         struct {
387                 __le32 flags;
388                 __le32 addr;
389         } cmd;
390
391         cmd.addr = cpu_to_le32(addr);
392         cmd.flags = cpu_to_le32(flags);
393         return qcom_scm_call(QCOM_SCM_SVC_BOOT, QCOM_SCM_BOOT_ADDR,
394                         &cmd, sizeof(cmd), NULL, 0);
395 }
396
397 /**
398  * qcom_scm_set_cold_boot_addr() - Set the cold boot address for cpus
399  * @entry: Entry point function for the cpus
400  * @cpus: The cpumask of cpus that will use the entry point
401  *
402  * Set the cold boot address of the cpus. Any cpu outside the supported
403  * range would be removed from the cpu present mask.
404  */
405 int __qcom_scm_set_cold_boot_addr(void *entry, const cpumask_t *cpus)
406 {
407         int flags = 0;
408         int cpu;
409         int scm_cb_flags[] = {
410                 QCOM_SCM_FLAG_COLDBOOT_CPU0,
411                 QCOM_SCM_FLAG_COLDBOOT_CPU1,
412                 QCOM_SCM_FLAG_COLDBOOT_CPU2,
413                 QCOM_SCM_FLAG_COLDBOOT_CPU3,
414         };
415
416         if (!cpus || (cpus && cpumask_empty(cpus)))
417                 return -EINVAL;
418
419         for_each_cpu(cpu, cpus) {
420                 if (cpu < ARRAY_SIZE(scm_cb_flags))
421                         flags |= scm_cb_flags[cpu];
422                 else
423                         set_cpu_present(cpu, false);
424         }
425
426         return qcom_scm_set_boot_addr(virt_to_phys(entry), flags);
427 }
428
429 /**
430  * qcom_scm_set_warm_boot_addr() - Set the warm boot address for cpus
431  * @entry: Entry point function for the cpus
432  * @cpus: The cpumask of cpus that will use the entry point
433  *
434  * Set the Linux entry point for the SCM to transfer control to when coming
435  * out of a power down. CPU power down may be executed on cpuidle or hotplug.
436  */
437 int __qcom_scm_set_warm_boot_addr(void *entry, const cpumask_t *cpus)
438 {
439         int ret;
440         int flags = 0;
441         int cpu;
442
443         /*
444          * Reassign only if we are switching from hotplug entry point
445          * to cpuidle entry point or vice versa.
446          */
447         for_each_cpu(cpu, cpus) {
448                 if (entry == qcom_scm_wb[cpu].entry)
449                         continue;
450                 flags |= qcom_scm_wb[cpu].flag;
451         }
452
453         /* No change in entry function */
454         if (!flags)
455                 return 0;
456
457         ret = qcom_scm_set_boot_addr(virt_to_phys(entry), flags);
458         if (!ret) {
459                 for_each_cpu(cpu, cpus)
460                         qcom_scm_wb[cpu].entry = entry;
461         }
462
463         return ret;
464 }
465
466 /**
467  * qcom_scm_cpu_power_down() - Power down the cpu
468  * @flags - Flags to flush cache
469  *
470  * This is an end point to power down cpu. If there was a pending interrupt,
471  * the control would return from this function, otherwise, the cpu jumps to the
472  * warm boot entry point set for this cpu upon reset.
473  */
474 void __qcom_scm_cpu_power_down(u32 flags)
475 {
476         qcom_scm_call_atomic1(QCOM_SCM_SVC_BOOT, QCOM_SCM_CMD_TERMINATE_PC,
477                         flags & QCOM_SCM_FLUSH_FLAG_MASK);
478 }
479
480 int __qcom_scm_is_call_available(u32 svc_id, u32 cmd_id)
481 {
482         int ret;
483         __le32 svc_cmd = cpu_to_le32((svc_id << 10) | cmd_id);
484         __le32 ret_val = 0;
485
486         ret = qcom_scm_call(QCOM_SCM_SVC_INFO, QCOM_IS_CALL_AVAIL_CMD, &svc_cmd,
487                         sizeof(svc_cmd), &ret_val, sizeof(ret_val));
488         if (ret)
489                 return ret;
490
491         return le32_to_cpu(ret_val);
492 }
493
494 int __qcom_scm_hdcp_req(struct qcom_scm_hdcp_req *req, u32 req_cnt, u32 *resp)
495 {
496         if (req_cnt > QCOM_SCM_HDCP_MAX_REQ_CNT)
497                 return -ERANGE;
498
499         return qcom_scm_call(QCOM_SCM_SVC_HDCP, QCOM_SCM_CMD_HDCP,
500                 req, req_cnt * sizeof(*req), resp, sizeof(*resp));
501 }