GNU Linux-libre 4.19.245-gnu1
[releases.git] / drivers / clk / qcom / lcc-mdm9615.c
1 /*
2  * Copyright (c) 2014, The Linux Foundation. All rights reserved.
3  * Copyright (c) BayLibre, SAS.
4  * Author : Neil Armstrong <narmstrong@baylibre.com>
5  *
6  * This software is licensed under the terms of the GNU General Public
7  * License version 2, as published by the Free Software Foundation, and
8  * may be copied, distributed, and modified under those terms.
9  *
10  * This program is distributed in the hope that it will be useful,
11  * but WITHOUT ANY WARRANTY; without even the implied warranty of
12  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13  * GNU General Public License for more details.
14  */
15
16 #include <linux/kernel.h>
17 #include <linux/bitops.h>
18 #include <linux/err.h>
19 #include <linux/platform_device.h>
20 #include <linux/module.h>
21 #include <linux/of.h>
22 #include <linux/of_device.h>
23 #include <linux/clk-provider.h>
24 #include <linux/regmap.h>
25
26 #include <dt-bindings/clock/qcom,lcc-mdm9615.h>
27
28 #include "common.h"
29 #include "clk-regmap.h"
30 #include "clk-pll.h"
31 #include "clk-rcg.h"
32 #include "clk-branch.h"
33 #include "clk-regmap-divider.h"
34 #include "clk-regmap-mux.h"
35
36 static struct clk_pll pll4 = {
37         .l_reg = 0x4,
38         .m_reg = 0x8,
39         .n_reg = 0xc,
40         .config_reg = 0x14,
41         .mode_reg = 0x0,
42         .status_reg = 0x18,
43         .status_bit = 16,
44         .clkr.hw.init = &(struct clk_init_data){
45                 .name = "pll4",
46                 .parent_names = (const char *[]){ "cxo" },
47                 .num_parents = 1,
48                 .ops = &clk_pll_ops,
49         },
50 };
51
52 enum {
53         P_CXO,
54         P_PLL4,
55 };
56
57 static const struct parent_map lcc_cxo_pll4_map[] = {
58         { P_CXO, 0 },
59         { P_PLL4, 2 }
60 };
61
62 static const char * const lcc_cxo_pll4[] = {
63         "cxo",
64         "pll4_vote",
65 };
66
67 static struct freq_tbl clk_tbl_aif_osr_492[] = {
68         {   512000, P_PLL4, 4, 1, 240 },
69         {   768000, P_PLL4, 4, 1, 160 },
70         {  1024000, P_PLL4, 4, 1, 120 },
71         {  1536000, P_PLL4, 4, 1,  80 },
72         {  2048000, P_PLL4, 4, 1,  60 },
73         {  3072000, P_PLL4, 4, 1,  40 },
74         {  4096000, P_PLL4, 4, 1,  30 },
75         {  6144000, P_PLL4, 4, 1,  20 },
76         {  8192000, P_PLL4, 4, 1,  15 },
77         { 12288000, P_PLL4, 4, 1,  10 },
78         { 24576000, P_PLL4, 4, 1,   5 },
79         { 27000000, P_CXO,  1, 0,   0 },
80         { }
81 };
82
83 static struct freq_tbl clk_tbl_aif_osr_393[] = {
84         {   512000, P_PLL4, 4, 1, 192 },
85         {   768000, P_PLL4, 4, 1, 128 },
86         {  1024000, P_PLL4, 4, 1,  96 },
87         {  1536000, P_PLL4, 4, 1,  64 },
88         {  2048000, P_PLL4, 4, 1,  48 },
89         {  3072000, P_PLL4, 4, 1,  32 },
90         {  4096000, P_PLL4, 4, 1,  24 },
91         {  6144000, P_PLL4, 4, 1,  16 },
92         {  8192000, P_PLL4, 4, 1,  12 },
93         { 12288000, P_PLL4, 4, 1,   8 },
94         { 24576000, P_PLL4, 4, 1,   4 },
95         { 27000000, P_CXO,  1, 0,   0 },
96         { }
97 };
98
99 static struct clk_rcg mi2s_osr_src = {
100         .ns_reg = 0x48,
101         .md_reg = 0x4c,
102         .mn = {
103                 .mnctr_en_bit = 8,
104                 .mnctr_reset_bit = 7,
105                 .mnctr_mode_shift = 5,
106                 .n_val_shift = 24,
107                 .m_val_shift = 8,
108                 .width = 8,
109         },
110         .p = {
111                 .pre_div_shift = 3,
112                 .pre_div_width = 2,
113         },
114         .s = {
115                 .src_sel_shift = 0,
116                 .parent_map = lcc_cxo_pll4_map,
117         },
118         .freq_tbl = clk_tbl_aif_osr_393,
119         .clkr = {
120                 .enable_reg = 0x48,
121                 .enable_mask = BIT(9),
122                 .hw.init = &(struct clk_init_data){
123                         .name = "mi2s_osr_src",
124                         .parent_names = lcc_cxo_pll4,
125                         .num_parents = 2,
126                         .ops = &clk_rcg_ops,
127                         .flags = CLK_SET_RATE_GATE,
128                 },
129         },
130 };
131
132 static const char * const lcc_mi2s_parents[] = {
133         "mi2s_osr_src",
134 };
135
136 static struct clk_branch mi2s_osr_clk = {
137         .halt_reg = 0x50,
138         .halt_bit = 1,
139         .halt_check = BRANCH_HALT_ENABLE,
140         .clkr = {
141                 .enable_reg = 0x48,
142                 .enable_mask = BIT(17),
143                 .hw.init = &(struct clk_init_data){
144                         .name = "mi2s_osr_clk",
145                         .parent_names = lcc_mi2s_parents,
146                         .num_parents = 1,
147                         .ops = &clk_branch_ops,
148                         .flags = CLK_SET_RATE_PARENT,
149                 },
150         },
151 };
152
153 static struct clk_regmap_div mi2s_div_clk = {
154         .reg = 0x48,
155         .shift = 10,
156         .width = 4,
157         .clkr = {
158                 .enable_reg = 0x48,
159                 .enable_mask = BIT(15),
160                 .hw.init = &(struct clk_init_data){
161                         .name = "mi2s_div_clk",
162                         .parent_names = lcc_mi2s_parents,
163                         .num_parents = 1,
164                         .ops = &clk_regmap_div_ops,
165                 },
166         },
167 };
168
169 static struct clk_branch mi2s_bit_div_clk = {
170         .halt_reg = 0x50,
171         .halt_bit = 0,
172         .halt_check = BRANCH_HALT_ENABLE,
173         .clkr = {
174                 .enable_reg = 0x48,
175                 .enable_mask = BIT(15),
176                 .hw.init = &(struct clk_init_data){
177                         .name = "mi2s_bit_div_clk",
178                         .parent_names = (const char *[]){ "mi2s_div_clk" },
179                         .num_parents = 1,
180                         .ops = &clk_branch_ops,
181                         .flags = CLK_SET_RATE_PARENT,
182                 },
183         },
184 };
185
186 static struct clk_regmap_mux mi2s_bit_clk = {
187         .reg = 0x48,
188         .shift = 14,
189         .width = 1,
190         .clkr = {
191                 .hw.init = &(struct clk_init_data){
192                         .name = "mi2s_bit_clk",
193                         .parent_names = (const char *[]){
194                                 "mi2s_bit_div_clk",
195                                 "mi2s_codec_clk",
196                         },
197                         .num_parents = 2,
198                         .ops = &clk_regmap_mux_closest_ops,
199                         .flags = CLK_SET_RATE_PARENT,
200                 },
201         },
202 };
203
204 #define CLK_AIF_OSR_DIV(prefix, _ns, _md, hr)                   \
205 static struct clk_rcg prefix##_osr_src = {                      \
206         .ns_reg = _ns,                                          \
207         .md_reg = _md,                                          \
208         .mn = {                                                 \
209                 .mnctr_en_bit = 8,                              \
210                 .mnctr_reset_bit = 7,                           \
211                 .mnctr_mode_shift = 5,                          \
212                 .n_val_shift = 24,                              \
213                 .m_val_shift = 8,                               \
214                 .width = 8,                                     \
215         },                                                      \
216         .p = {                                                  \
217                 .pre_div_shift = 3,                             \
218                 .pre_div_width = 2,                             \
219         },                                                      \
220         .s = {                                                  \
221                 .src_sel_shift = 0,                             \
222                 .parent_map = lcc_cxo_pll4_map,                 \
223         },                                                      \
224         .freq_tbl = clk_tbl_aif_osr_393,                        \
225         .clkr = {                                               \
226                 .enable_reg = _ns,                              \
227                 .enable_mask = BIT(9),                          \
228                 .hw.init = &(struct clk_init_data){             \
229                         .name = #prefix "_osr_src",             \
230                         .parent_names = lcc_cxo_pll4,           \
231                         .num_parents = 2,                       \
232                         .ops = &clk_rcg_ops,                    \
233                         .flags = CLK_SET_RATE_GATE,             \
234                 },                                              \
235         },                                                      \
236 };                                                              \
237                                                                 \
238 static const char * const lcc_##prefix##_parents[] = {          \
239         #prefix "_osr_src",                                     \
240 };                                                              \
241                                                                 \
242 static struct clk_branch prefix##_osr_clk = {                   \
243         .halt_reg = hr,                                         \
244         .halt_bit = 1,                                          \
245         .halt_check = BRANCH_HALT_ENABLE,                       \
246         .clkr = {                                               \
247                 .enable_reg = _ns,                              \
248                 .enable_mask = BIT(21),                         \
249                 .hw.init = &(struct clk_init_data){             \
250                         .name = #prefix "_osr_clk",             \
251                         .parent_names = lcc_##prefix##_parents, \
252                         .num_parents = 1,                       \
253                         .ops = &clk_branch_ops,                 \
254                         .flags = CLK_SET_RATE_PARENT,           \
255                 },                                              \
256         },                                                      \
257 };                                                              \
258                                                                 \
259 static struct clk_regmap_div prefix##_div_clk = {               \
260         .reg = _ns,                                             \
261         .shift = 10,                                            \
262         .width = 8,                                             \
263         .clkr = {                                               \
264                 .hw.init = &(struct clk_init_data){             \
265                         .name = #prefix "_div_clk",             \
266                         .parent_names = lcc_##prefix##_parents, \
267                         .num_parents = 1,                       \
268                         .ops = &clk_regmap_div_ops,             \
269                 },                                              \
270         },                                                      \
271 };                                                              \
272                                                                 \
273 static struct clk_branch prefix##_bit_div_clk = {               \
274         .halt_reg = hr,                                         \
275         .halt_bit = 0,                                          \
276         .halt_check = BRANCH_HALT_ENABLE,                       \
277         .clkr = {                                               \
278                 .enable_reg = _ns,                              \
279                 .enable_mask = BIT(19),                         \
280                 .hw.init = &(struct clk_init_data){             \
281                         .name = #prefix "_bit_div_clk",         \
282                         .parent_names = (const char *[]){       \
283                                 #prefix "_div_clk"              \
284                         },                                      \
285                         .num_parents = 1,                       \
286                         .ops = &clk_branch_ops,                 \
287                         .flags = CLK_SET_RATE_PARENT,           \
288                 },                                              \
289         },                                                      \
290 };                                                              \
291                                                                 \
292 static struct clk_regmap_mux prefix##_bit_clk = {               \
293         .reg = _ns,                                             \
294         .shift = 18,                                            \
295         .width = 1,                                             \
296         .clkr = {                                               \
297                 .hw.init = &(struct clk_init_data){             \
298                         .name = #prefix "_bit_clk",             \
299                         .parent_names = (const char *[]){       \
300                                 #prefix "_bit_div_clk",         \
301                                 #prefix "_codec_clk",           \
302                         },                                      \
303                         .num_parents = 2,                       \
304                         .ops = &clk_regmap_mux_closest_ops,     \
305                         .flags = CLK_SET_RATE_PARENT,           \
306                 },                                              \
307         },                                                      \
308 }
309
310 CLK_AIF_OSR_DIV(codec_i2s_mic, 0x60, 0x64, 0x68);
311 CLK_AIF_OSR_DIV(spare_i2s_mic, 0x78, 0x7c, 0x80);
312 CLK_AIF_OSR_DIV(codec_i2s_spkr, 0x6c, 0x70, 0x74);
313 CLK_AIF_OSR_DIV(spare_i2s_spkr, 0x84, 0x88, 0x8c);
314
315 static struct freq_tbl clk_tbl_pcm_492[] = {
316         {   256000, P_PLL4, 4, 1, 480 },
317         {   512000, P_PLL4, 4, 1, 240 },
318         {   768000, P_PLL4, 4, 1, 160 },
319         {  1024000, P_PLL4, 4, 1, 120 },
320         {  1536000, P_PLL4, 4, 1,  80 },
321         {  2048000, P_PLL4, 4, 1,  60 },
322         {  3072000, P_PLL4, 4, 1,  40 },
323         {  4096000, P_PLL4, 4, 1,  30 },
324         {  6144000, P_PLL4, 4, 1,  20 },
325         {  8192000, P_PLL4, 4, 1,  15 },
326         { 12288000, P_PLL4, 4, 1,  10 },
327         { 24576000, P_PLL4, 4, 1,   5 },
328         { 27000000, P_CXO,  1, 0,   0 },
329         { }
330 };
331
332 static struct freq_tbl clk_tbl_pcm_393[] = {
333         {   256000, P_PLL4, 4, 1, 384 },
334         {   512000, P_PLL4, 4, 1, 192 },
335         {   768000, P_PLL4, 4, 1, 128 },
336         {  1024000, P_PLL4, 4, 1,  96 },
337         {  1536000, P_PLL4, 4, 1,  64 },
338         {  2048000, P_PLL4, 4, 1,  48 },
339         {  3072000, P_PLL4, 4, 1,  32 },
340         {  4096000, P_PLL4, 4, 1,  24 },
341         {  6144000, P_PLL4, 4, 1,  16 },
342         {  8192000, P_PLL4, 4, 1,  12 },
343         { 12288000, P_PLL4, 4, 1,   8 },
344         { 24576000, P_PLL4, 4, 1,   4 },
345         { 27000000, P_CXO,  1, 0,   0 },
346         { }
347 };
348
349 static struct clk_rcg pcm_src = {
350         .ns_reg = 0x54,
351         .md_reg = 0x58,
352         .mn = {
353                 .mnctr_en_bit = 8,
354                 .mnctr_reset_bit = 7,
355                 .mnctr_mode_shift = 5,
356                 .n_val_shift = 16,
357                 .m_val_shift = 16,
358                 .width = 16,
359         },
360         .p = {
361                 .pre_div_shift = 3,
362                 .pre_div_width = 2,
363         },
364         .s = {
365                 .src_sel_shift = 0,
366                 .parent_map = lcc_cxo_pll4_map,
367         },
368         .freq_tbl = clk_tbl_pcm_393,
369         .clkr = {
370                 .enable_reg = 0x54,
371                 .enable_mask = BIT(9),
372                 .hw.init = &(struct clk_init_data){
373                         .name = "pcm_src",
374                         .parent_names = lcc_cxo_pll4,
375                         .num_parents = 2,
376                         .ops = &clk_rcg_ops,
377                         .flags = CLK_SET_RATE_GATE,
378                 },
379         },
380 };
381
382 static struct clk_branch pcm_clk_out = {
383         .halt_reg = 0x5c,
384         .halt_bit = 0,
385         .halt_check = BRANCH_HALT_ENABLE,
386         .clkr = {
387                 .enable_reg = 0x54,
388                 .enable_mask = BIT(11),
389                 .hw.init = &(struct clk_init_data){
390                         .name = "pcm_clk_out",
391                         .parent_names = (const char *[]){ "pcm_src" },
392                         .num_parents = 1,
393                         .ops = &clk_branch_ops,
394                         .flags = CLK_SET_RATE_PARENT,
395                 },
396         },
397 };
398
399 static struct clk_regmap_mux pcm_clk = {
400         .reg = 0x54,
401         .shift = 10,
402         .width = 1,
403         .clkr = {
404                 .hw.init = &(struct clk_init_data){
405                         .name = "pcm_clk",
406                         .parent_names = (const char *[]){
407                                 "pcm_clk_out",
408                                 "pcm_codec_clk",
409                         },
410                         .num_parents = 2,
411                         .ops = &clk_regmap_mux_closest_ops,
412                         .flags = CLK_SET_RATE_PARENT,
413                 },
414         },
415 };
416
417 static struct clk_rcg slimbus_src = {
418         .ns_reg = 0xcc,
419         .md_reg = 0xd0,
420         .mn = {
421                 .mnctr_en_bit = 8,
422                 .mnctr_reset_bit = 7,
423                 .mnctr_mode_shift = 5,
424                 .n_val_shift = 24,
425                 .m_val_shift = 8,
426                 .width = 8,
427         },
428         .p = {
429                 .pre_div_shift = 3,
430                 .pre_div_width = 2,
431         },
432         .s = {
433                 .src_sel_shift = 0,
434                 .parent_map = lcc_cxo_pll4_map,
435         },
436         .freq_tbl = clk_tbl_aif_osr_393,
437         .clkr = {
438                 .enable_reg = 0xcc,
439                 .enable_mask = BIT(9),
440                 .hw.init = &(struct clk_init_data){
441                         .name = "slimbus_src",
442                         .parent_names = lcc_cxo_pll4,
443                         .num_parents = 2,
444                         .ops = &clk_rcg_ops,
445                         .flags = CLK_SET_RATE_GATE,
446                 },
447         },
448 };
449
450 static const char * const lcc_slimbus_parents[] = {
451         "slimbus_src",
452 };
453
454 static struct clk_branch audio_slimbus_clk = {
455         .halt_reg = 0xd4,
456         .halt_bit = 0,
457         .halt_check = BRANCH_HALT_ENABLE,
458         .clkr = {
459                 .enable_reg = 0xcc,
460                 .enable_mask = BIT(10),
461                 .hw.init = &(struct clk_init_data){
462                         .name = "audio_slimbus_clk",
463                         .parent_names = lcc_slimbus_parents,
464                         .num_parents = 1,
465                         .ops = &clk_branch_ops,
466                         .flags = CLK_SET_RATE_PARENT,
467                 },
468         },
469 };
470
471 static struct clk_branch sps_slimbus_clk = {
472         .halt_reg = 0xd4,
473         .halt_bit = 1,
474         .halt_check = BRANCH_HALT_ENABLE,
475         .clkr = {
476                 .enable_reg = 0xcc,
477                 .enable_mask = BIT(12),
478                 .hw.init = &(struct clk_init_data){
479                         .name = "sps_slimbus_clk",
480                         .parent_names = lcc_slimbus_parents,
481                         .num_parents = 1,
482                         .ops = &clk_branch_ops,
483                         .flags = CLK_SET_RATE_PARENT,
484                 },
485         },
486 };
487
488 static struct clk_regmap *lcc_mdm9615_clks[] = {
489         [PLL4] = &pll4.clkr,
490         [MI2S_OSR_SRC] = &mi2s_osr_src.clkr,
491         [MI2S_OSR_CLK] = &mi2s_osr_clk.clkr,
492         [MI2S_DIV_CLK] = &mi2s_div_clk.clkr,
493         [MI2S_BIT_DIV_CLK] = &mi2s_bit_div_clk.clkr,
494         [MI2S_BIT_CLK] = &mi2s_bit_clk.clkr,
495         [PCM_SRC] = &pcm_src.clkr,
496         [PCM_CLK_OUT] = &pcm_clk_out.clkr,
497         [PCM_CLK] = &pcm_clk.clkr,
498         [SLIMBUS_SRC] = &slimbus_src.clkr,
499         [AUDIO_SLIMBUS_CLK] = &audio_slimbus_clk.clkr,
500         [SPS_SLIMBUS_CLK] = &sps_slimbus_clk.clkr,
501         [CODEC_I2S_MIC_OSR_SRC] = &codec_i2s_mic_osr_src.clkr,
502         [CODEC_I2S_MIC_OSR_CLK] = &codec_i2s_mic_osr_clk.clkr,
503         [CODEC_I2S_MIC_DIV_CLK] = &codec_i2s_mic_div_clk.clkr,
504         [CODEC_I2S_MIC_BIT_DIV_CLK] = &codec_i2s_mic_bit_div_clk.clkr,
505         [CODEC_I2S_MIC_BIT_CLK] = &codec_i2s_mic_bit_clk.clkr,
506         [SPARE_I2S_MIC_OSR_SRC] = &spare_i2s_mic_osr_src.clkr,
507         [SPARE_I2S_MIC_OSR_CLK] = &spare_i2s_mic_osr_clk.clkr,
508         [SPARE_I2S_MIC_DIV_CLK] = &spare_i2s_mic_div_clk.clkr,
509         [SPARE_I2S_MIC_BIT_DIV_CLK] = &spare_i2s_mic_bit_div_clk.clkr,
510         [SPARE_I2S_MIC_BIT_CLK] = &spare_i2s_mic_bit_clk.clkr,
511         [CODEC_I2S_SPKR_OSR_SRC] = &codec_i2s_spkr_osr_src.clkr,
512         [CODEC_I2S_SPKR_OSR_CLK] = &codec_i2s_spkr_osr_clk.clkr,
513         [CODEC_I2S_SPKR_DIV_CLK] = &codec_i2s_spkr_div_clk.clkr,
514         [CODEC_I2S_SPKR_BIT_DIV_CLK] = &codec_i2s_spkr_bit_div_clk.clkr,
515         [CODEC_I2S_SPKR_BIT_CLK] = &codec_i2s_spkr_bit_clk.clkr,
516         [SPARE_I2S_SPKR_OSR_SRC] = &spare_i2s_spkr_osr_src.clkr,
517         [SPARE_I2S_SPKR_OSR_CLK] = &spare_i2s_spkr_osr_clk.clkr,
518         [SPARE_I2S_SPKR_DIV_CLK] = &spare_i2s_spkr_div_clk.clkr,
519         [SPARE_I2S_SPKR_BIT_DIV_CLK] = &spare_i2s_spkr_bit_div_clk.clkr,
520         [SPARE_I2S_SPKR_BIT_CLK] = &spare_i2s_spkr_bit_clk.clkr,
521 };
522
523 static const struct regmap_config lcc_mdm9615_regmap_config = {
524         .reg_bits       = 32,
525         .reg_stride     = 4,
526         .val_bits       = 32,
527         .max_register   = 0xfc,
528         .fast_io        = true,
529 };
530
531 static const struct qcom_cc_desc lcc_mdm9615_desc = {
532         .config = &lcc_mdm9615_regmap_config,
533         .clks = lcc_mdm9615_clks,
534         .num_clks = ARRAY_SIZE(lcc_mdm9615_clks),
535 };
536
537 static const struct of_device_id lcc_mdm9615_match_table[] = {
538         { .compatible = "qcom,lcc-mdm9615" },
539         { }
540 };
541 MODULE_DEVICE_TABLE(of, lcc_mdm9615_match_table);
542
543 static int lcc_mdm9615_probe(struct platform_device *pdev)
544 {
545         u32 val;
546         struct regmap *regmap;
547
548         regmap = qcom_cc_map(pdev, &lcc_mdm9615_desc);
549         if (IS_ERR(regmap))
550                 return PTR_ERR(regmap);
551
552         /* Use the correct frequency plan depending on speed of PLL4 */
553         regmap_read(regmap, 0x4, &val);
554         if (val == 0x12) {
555                 slimbus_src.freq_tbl = clk_tbl_aif_osr_492;
556                 mi2s_osr_src.freq_tbl = clk_tbl_aif_osr_492;
557                 codec_i2s_mic_osr_src.freq_tbl = clk_tbl_aif_osr_492;
558                 spare_i2s_mic_osr_src.freq_tbl = clk_tbl_aif_osr_492;
559                 codec_i2s_spkr_osr_src.freq_tbl = clk_tbl_aif_osr_492;
560                 spare_i2s_spkr_osr_src.freq_tbl = clk_tbl_aif_osr_492;
561                 pcm_src.freq_tbl = clk_tbl_pcm_492;
562         }
563         /* Enable PLL4 source on the LPASS Primary PLL Mux */
564         regmap_write(regmap, 0xc4, 0x1);
565
566         return qcom_cc_really_probe(pdev, &lcc_mdm9615_desc, regmap);
567 }
568
569 static struct platform_driver lcc_mdm9615_driver = {
570         .probe          = lcc_mdm9615_probe,
571         .driver         = {
572                 .name   = "lcc-mdm9615",
573                 .of_match_table = lcc_mdm9615_match_table,
574         },
575 };
576 module_platform_driver(lcc_mdm9615_driver);
577
578 MODULE_DESCRIPTION("QCOM LCC MDM9615 Driver");
579 MODULE_LICENSE("GPL v2");
580 MODULE_ALIAS("platform:lcc-mdm9615");