omap_clk.c 30 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239124012411242124312441245124612471248124912501251125212531254125512561257125812591260
  1. /*
  2. * OMAP clocks.
  3. *
  4. * Copyright (C) 2006-2008 Andrzej Zaborowski <balrog@zabor.org>
  5. *
  6. * Clocks data comes in part from arch/arm/mach-omap1/clock.h in Linux.
  7. *
  8. * This program is free software; you can redistribute it and/or
  9. * modify it under the terms of the GNU General Public License as
  10. * published by the Free Software Foundation; either version 2 of
  11. * the License, or (at your option) any later version.
  12. *
  13. * This program is distributed in the hope that it will be useful,
  14. * but WITHOUT ANY WARRANTY; without even the implied warranty of
  15. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  16. * GNU General Public License for more details.
  17. *
  18. * You should have received a copy of the GNU General Public License along
  19. * with this program; if not, see <http://www.gnu.org/licenses/>.
  20. */
  21. #include "hw.h"
  22. #include "omap.h"
  23. struct clk {
  24. const char *name;
  25. const char *alias;
  26. struct clk *parent;
  27. struct clk *child1;
  28. struct clk *sibling;
  29. #define ALWAYS_ENABLED (1 << 0)
  30. #define CLOCK_IN_OMAP310 (1 << 10)
  31. #define CLOCK_IN_OMAP730 (1 << 11)
  32. #define CLOCK_IN_OMAP1510 (1 << 12)
  33. #define CLOCK_IN_OMAP16XX (1 << 13)
  34. #define CLOCK_IN_OMAP242X (1 << 14)
  35. #define CLOCK_IN_OMAP243X (1 << 15)
  36. #define CLOCK_IN_OMAP343X (1 << 16)
  37. uint32_t flags;
  38. int id;
  39. int running; /* Is currently ticking */
  40. int enabled; /* Is enabled, regardless of its input clk */
  41. unsigned long rate; /* Current rate (if .running) */
  42. unsigned int divisor; /* Rate relative to input (if .enabled) */
  43. unsigned int multiplier; /* Rate relative to input (if .enabled) */
  44. qemu_irq users[16]; /* Who to notify on change */
  45. int usecount; /* Automatically idle when unused */
  46. };
  47. static struct clk xtal_osc12m = {
  48. .name = "xtal_osc_12m",
  49. .rate = 12000000,
  50. .flags = CLOCK_IN_OMAP1510 | CLOCK_IN_OMAP16XX | CLOCK_IN_OMAP310,
  51. };
  52. static struct clk xtal_osc32k = {
  53. .name = "xtal_osc_32k",
  54. .rate = 32768,
  55. .flags = CLOCK_IN_OMAP1510 | CLOCK_IN_OMAP16XX | CLOCK_IN_OMAP310 |
  56. CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  57. };
  58. static struct clk ck_ref = {
  59. .name = "ck_ref",
  60. .alias = "clkin",
  61. .parent = &xtal_osc12m,
  62. .flags = CLOCK_IN_OMAP1510 | CLOCK_IN_OMAP16XX | CLOCK_IN_OMAP310 |
  63. ALWAYS_ENABLED,
  64. };
  65. /* If a dpll is disabled it becomes a bypass, child clocks don't stop */
  66. static struct clk dpll1 = {
  67. .name = "dpll1",
  68. .parent = &ck_ref,
  69. .flags = CLOCK_IN_OMAP1510 | CLOCK_IN_OMAP16XX | CLOCK_IN_OMAP310 |
  70. ALWAYS_ENABLED,
  71. };
  72. static struct clk dpll2 = {
  73. .name = "dpll2",
  74. .parent = &ck_ref,
  75. .flags = CLOCK_IN_OMAP310 | ALWAYS_ENABLED,
  76. };
  77. static struct clk dpll3 = {
  78. .name = "dpll3",
  79. .parent = &ck_ref,
  80. .flags = CLOCK_IN_OMAP310 | ALWAYS_ENABLED,
  81. };
  82. static struct clk dpll4 = {
  83. .name = "dpll4",
  84. .parent = &ck_ref,
  85. .multiplier = 4,
  86. .flags = CLOCK_IN_OMAP1510 | CLOCK_IN_OMAP16XX | CLOCK_IN_OMAP310,
  87. };
  88. static struct clk apll = {
  89. .name = "apll",
  90. .parent = &ck_ref,
  91. .multiplier = 48,
  92. .divisor = 12,
  93. .flags = CLOCK_IN_OMAP1510 | CLOCK_IN_OMAP16XX | CLOCK_IN_OMAP310,
  94. };
  95. static struct clk ck_48m = {
  96. .name = "ck_48m",
  97. .parent = &dpll4, /* either dpll4 or apll */
  98. .flags = CLOCK_IN_OMAP1510 | CLOCK_IN_OMAP16XX | CLOCK_IN_OMAP310,
  99. };
  100. static struct clk ck_dpll1out = {
  101. .name = "ck_dpll1out",
  102. .parent = &dpll1,
  103. .flags = CLOCK_IN_OMAP16XX,
  104. };
  105. static struct clk sossi_ck = {
  106. .name = "ck_sossi",
  107. .parent = &ck_dpll1out,
  108. .flags = CLOCK_IN_OMAP16XX,
  109. };
  110. static struct clk clkm1 = {
  111. .name = "clkm1",
  112. .alias = "ck_gen1",
  113. .parent = &dpll1,
  114. .flags = CLOCK_IN_OMAP1510 | CLOCK_IN_OMAP16XX | CLOCK_IN_OMAP310 |
  115. ALWAYS_ENABLED,
  116. };
  117. static struct clk clkm2 = {
  118. .name = "clkm2",
  119. .alias = "ck_gen2",
  120. .parent = &dpll1,
  121. .flags = CLOCK_IN_OMAP1510 | CLOCK_IN_OMAP16XX | CLOCK_IN_OMAP310 |
  122. ALWAYS_ENABLED,
  123. };
  124. static struct clk clkm3 = {
  125. .name = "clkm3",
  126. .alias = "ck_gen3",
  127. .parent = &dpll1, /* either dpll1 or ck_ref */
  128. .flags = CLOCK_IN_OMAP1510 | CLOCK_IN_OMAP16XX | CLOCK_IN_OMAP310 |
  129. ALWAYS_ENABLED,
  130. };
  131. static struct clk arm_ck = {
  132. .name = "arm_ck",
  133. .alias = "mpu_ck",
  134. .parent = &clkm1,
  135. .flags = CLOCK_IN_OMAP1510 | CLOCK_IN_OMAP16XX | CLOCK_IN_OMAP310 |
  136. ALWAYS_ENABLED,
  137. };
  138. static struct clk armper_ck = {
  139. .name = "armper_ck",
  140. .alias = "mpuper_ck",
  141. .parent = &clkm1,
  142. .flags = CLOCK_IN_OMAP1510 | CLOCK_IN_OMAP16XX | CLOCK_IN_OMAP310,
  143. };
  144. static struct clk arm_gpio_ck = {
  145. .name = "arm_gpio_ck",
  146. .alias = "mpu_gpio_ck",
  147. .parent = &clkm1,
  148. .divisor = 1,
  149. .flags = CLOCK_IN_OMAP1510 | CLOCK_IN_OMAP310,
  150. };
  151. static struct clk armxor_ck = {
  152. .name = "armxor_ck",
  153. .alias = "mpuxor_ck",
  154. .parent = &ck_ref,
  155. .flags = CLOCK_IN_OMAP1510 | CLOCK_IN_OMAP16XX | CLOCK_IN_OMAP310,
  156. };
  157. static struct clk armtim_ck = {
  158. .name = "armtim_ck",
  159. .alias = "mputim_ck",
  160. .parent = &ck_ref, /* either CLKIN or DPLL1 */
  161. .flags = CLOCK_IN_OMAP1510 | CLOCK_IN_OMAP16XX | CLOCK_IN_OMAP310,
  162. };
  163. static struct clk armwdt_ck = {
  164. .name = "armwdt_ck",
  165. .alias = "mpuwd_ck",
  166. .parent = &clkm1,
  167. .divisor = 14,
  168. .flags = CLOCK_IN_OMAP1510 | CLOCK_IN_OMAP16XX | CLOCK_IN_OMAP310 |
  169. ALWAYS_ENABLED,
  170. };
  171. static struct clk arminth_ck16xx = {
  172. .name = "arminth_ck",
  173. .parent = &arm_ck,
  174. .flags = CLOCK_IN_OMAP16XX | ALWAYS_ENABLED,
  175. /* Note: On 16xx the frequency can be divided by 2 by programming
  176. * ARM_CKCTL:ARM_INTHCK_SEL(14) to 1
  177. *
  178. * 1510 version is in TC clocks.
  179. */
  180. };
  181. static struct clk dsp_ck = {
  182. .name = "dsp_ck",
  183. .parent = &clkm2,
  184. .flags = CLOCK_IN_OMAP310 | CLOCK_IN_OMAP1510 | CLOCK_IN_OMAP16XX,
  185. };
  186. static struct clk dspmmu_ck = {
  187. .name = "dspmmu_ck",
  188. .parent = &clkm2,
  189. .flags = CLOCK_IN_OMAP310 | CLOCK_IN_OMAP1510 | CLOCK_IN_OMAP16XX |
  190. ALWAYS_ENABLED,
  191. };
  192. static struct clk dspper_ck = {
  193. .name = "dspper_ck",
  194. .parent = &clkm2,
  195. .flags = CLOCK_IN_OMAP310 | CLOCK_IN_OMAP1510 | CLOCK_IN_OMAP16XX,
  196. };
  197. static struct clk dspxor_ck = {
  198. .name = "dspxor_ck",
  199. .parent = &ck_ref,
  200. .flags = CLOCK_IN_OMAP310 | CLOCK_IN_OMAP1510 | CLOCK_IN_OMAP16XX,
  201. };
  202. static struct clk dsptim_ck = {
  203. .name = "dsptim_ck",
  204. .parent = &ck_ref,
  205. .flags = CLOCK_IN_OMAP310 | CLOCK_IN_OMAP1510 | CLOCK_IN_OMAP16XX,
  206. };
  207. static struct clk tc_ck = {
  208. .name = "tc_ck",
  209. .parent = &clkm3,
  210. .flags = CLOCK_IN_OMAP1510 | CLOCK_IN_OMAP16XX |
  211. CLOCK_IN_OMAP730 | CLOCK_IN_OMAP310 |
  212. ALWAYS_ENABLED,
  213. };
  214. static struct clk arminth_ck15xx = {
  215. .name = "arminth_ck",
  216. .parent = &tc_ck,
  217. .flags = CLOCK_IN_OMAP1510 | CLOCK_IN_OMAP310 | ALWAYS_ENABLED,
  218. /* Note: On 1510 the frequency follows TC_CK
  219. *
  220. * 16xx version is in MPU clocks.
  221. */
  222. };
  223. static struct clk tipb_ck = {
  224. /* No-idle controlled by "tc_ck" */
  225. .name = "tipb_ck",
  226. .parent = &tc_ck,
  227. .flags = CLOCK_IN_OMAP1510 | CLOCK_IN_OMAP310 | ALWAYS_ENABLED,
  228. };
  229. static struct clk l3_ocpi_ck = {
  230. /* No-idle controlled by "tc_ck" */
  231. .name = "l3_ocpi_ck",
  232. .parent = &tc_ck,
  233. .flags = CLOCK_IN_OMAP16XX,
  234. };
  235. static struct clk tc1_ck = {
  236. .name = "tc1_ck",
  237. .parent = &tc_ck,
  238. .flags = CLOCK_IN_OMAP16XX,
  239. };
  240. static struct clk tc2_ck = {
  241. .name = "tc2_ck",
  242. .parent = &tc_ck,
  243. .flags = CLOCK_IN_OMAP16XX,
  244. };
  245. static struct clk dma_ck = {
  246. /* No-idle controlled by "tc_ck" */
  247. .name = "dma_ck",
  248. .parent = &tc_ck,
  249. .flags = CLOCK_IN_OMAP1510 | CLOCK_IN_OMAP16XX | CLOCK_IN_OMAP310 |
  250. ALWAYS_ENABLED,
  251. };
  252. static struct clk dma_lcdfree_ck = {
  253. .name = "dma_lcdfree_ck",
  254. .parent = &tc_ck,
  255. .flags = CLOCK_IN_OMAP16XX | ALWAYS_ENABLED,
  256. };
  257. static struct clk api_ck = {
  258. .name = "api_ck",
  259. .alias = "mpui_ck",
  260. .parent = &tc_ck,
  261. .flags = CLOCK_IN_OMAP1510 | CLOCK_IN_OMAP16XX | CLOCK_IN_OMAP310,
  262. };
  263. static struct clk lb_ck = {
  264. .name = "lb_ck",
  265. .parent = &tc_ck,
  266. .flags = CLOCK_IN_OMAP1510 | CLOCK_IN_OMAP310,
  267. };
  268. static struct clk lbfree_ck = {
  269. .name = "lbfree_ck",
  270. .parent = &tc_ck,
  271. .flags = CLOCK_IN_OMAP1510 | CLOCK_IN_OMAP310,
  272. };
  273. static struct clk hsab_ck = {
  274. .name = "hsab_ck",
  275. .parent = &tc_ck,
  276. .flags = CLOCK_IN_OMAP1510 | CLOCK_IN_OMAP310,
  277. };
  278. static struct clk rhea1_ck = {
  279. .name = "rhea1_ck",
  280. .parent = &tc_ck,
  281. .flags = CLOCK_IN_OMAP16XX | ALWAYS_ENABLED,
  282. };
  283. static struct clk rhea2_ck = {
  284. .name = "rhea2_ck",
  285. .parent = &tc_ck,
  286. .flags = CLOCK_IN_OMAP16XX | ALWAYS_ENABLED,
  287. };
  288. static struct clk lcd_ck_16xx = {
  289. .name = "lcd_ck",
  290. .parent = &clkm3,
  291. .flags = CLOCK_IN_OMAP16XX | CLOCK_IN_OMAP730,
  292. };
  293. static struct clk lcd_ck_1510 = {
  294. .name = "lcd_ck",
  295. .parent = &clkm3,
  296. .flags = CLOCK_IN_OMAP1510 | CLOCK_IN_OMAP310,
  297. };
  298. static struct clk uart1_1510 = {
  299. .name = "uart1_ck",
  300. /* Direct from ULPD, no real parent */
  301. .parent = &armper_ck, /* either armper_ck or dpll4 */
  302. .rate = 12000000,
  303. .flags = CLOCK_IN_OMAP1510 | CLOCK_IN_OMAP310 | ALWAYS_ENABLED,
  304. };
  305. static struct clk uart1_16xx = {
  306. .name = "uart1_ck",
  307. /* Direct from ULPD, no real parent */
  308. .parent = &armper_ck,
  309. .rate = 48000000,
  310. .flags = CLOCK_IN_OMAP16XX,
  311. };
  312. static struct clk uart2_ck = {
  313. .name = "uart2_ck",
  314. /* Direct from ULPD, no real parent */
  315. .parent = &armper_ck, /* either armper_ck or dpll4 */
  316. .rate = 12000000,
  317. .flags = CLOCK_IN_OMAP1510 | CLOCK_IN_OMAP16XX | CLOCK_IN_OMAP310 |
  318. ALWAYS_ENABLED,
  319. };
  320. static struct clk uart3_1510 = {
  321. .name = "uart3_ck",
  322. /* Direct from ULPD, no real parent */
  323. .parent = &armper_ck, /* either armper_ck or dpll4 */
  324. .rate = 12000000,
  325. .flags = CLOCK_IN_OMAP1510 | CLOCK_IN_OMAP310 | ALWAYS_ENABLED,
  326. };
  327. static struct clk uart3_16xx = {
  328. .name = "uart3_ck",
  329. /* Direct from ULPD, no real parent */
  330. .parent = &armper_ck,
  331. .rate = 48000000,
  332. .flags = CLOCK_IN_OMAP16XX,
  333. };
  334. static struct clk usb_clk0 = { /* 6 MHz output on W4_USB_CLK0 */
  335. .name = "usb_clk0",
  336. .alias = "usb.clko",
  337. /* Direct from ULPD, no parent */
  338. .rate = 6000000,
  339. .flags = CLOCK_IN_OMAP1510 | CLOCK_IN_OMAP16XX | CLOCK_IN_OMAP310,
  340. };
  341. static struct clk usb_hhc_ck1510 = {
  342. .name = "usb_hhc_ck",
  343. /* Direct from ULPD, no parent */
  344. .rate = 48000000, /* Actually 2 clocks, 12MHz and 48MHz */
  345. .flags = CLOCK_IN_OMAP1510 | CLOCK_IN_OMAP310,
  346. };
  347. static struct clk usb_hhc_ck16xx = {
  348. .name = "usb_hhc_ck",
  349. /* Direct from ULPD, no parent */
  350. .rate = 48000000,
  351. /* OTG_SYSCON_2.OTG_PADEN == 0 (not 1510-compatible) */
  352. .flags = CLOCK_IN_OMAP16XX,
  353. };
  354. static struct clk usb_w2fc_mclk = {
  355. .name = "usb_w2fc_mclk",
  356. .alias = "usb_w2fc_ck",
  357. .parent = &ck_48m,
  358. .rate = 48000000,
  359. .flags = CLOCK_IN_OMAP310 | CLOCK_IN_OMAP1510 | CLOCK_IN_OMAP16XX,
  360. };
  361. static struct clk mclk_1510 = {
  362. .name = "mclk",
  363. /* Direct from ULPD, no parent. May be enabled by ext hardware. */
  364. .rate = 12000000,
  365. .flags = CLOCK_IN_OMAP1510,
  366. };
  367. static struct clk bclk_310 = {
  368. .name = "bt_mclk_out", /* Alias midi_mclk_out? */
  369. .parent = &armper_ck,
  370. .flags = CLOCK_IN_OMAP310,
  371. };
  372. static struct clk mclk_310 = {
  373. .name = "com_mclk_out",
  374. .parent = &armper_ck,
  375. .flags = CLOCK_IN_OMAP310,
  376. };
  377. static struct clk mclk_16xx = {
  378. .name = "mclk",
  379. /* Direct from ULPD, no parent. May be enabled by ext hardware. */
  380. .flags = CLOCK_IN_OMAP16XX,
  381. };
  382. static struct clk bclk_1510 = {
  383. .name = "bclk",
  384. /* Direct from ULPD, no parent. May be enabled by ext hardware. */
  385. .rate = 12000000,
  386. .flags = CLOCK_IN_OMAP1510,
  387. };
  388. static struct clk bclk_16xx = {
  389. .name = "bclk",
  390. /* Direct from ULPD, no parent. May be enabled by ext hardware. */
  391. .flags = CLOCK_IN_OMAP16XX,
  392. };
  393. static struct clk mmc1_ck = {
  394. .name = "mmc_ck",
  395. .id = 1,
  396. /* Functional clock is direct from ULPD, interface clock is ARMPER */
  397. .parent = &armper_ck, /* either armper_ck or dpll4 */
  398. .rate = 48000000,
  399. .flags = CLOCK_IN_OMAP1510 | CLOCK_IN_OMAP16XX | CLOCK_IN_OMAP310,
  400. };
  401. static struct clk mmc2_ck = {
  402. .name = "mmc_ck",
  403. .id = 2,
  404. /* Functional clock is direct from ULPD, interface clock is ARMPER */
  405. .parent = &armper_ck,
  406. .rate = 48000000,
  407. .flags = CLOCK_IN_OMAP16XX,
  408. };
  409. static struct clk cam_mclk = {
  410. .name = "cam.mclk",
  411. .flags = CLOCK_IN_OMAP310 | CLOCK_IN_OMAP1510 | CLOCK_IN_OMAP16XX,
  412. .rate = 12000000,
  413. };
  414. static struct clk cam_exclk = {
  415. .name = "cam.exclk",
  416. .flags = CLOCK_IN_OMAP310 | CLOCK_IN_OMAP1510 | CLOCK_IN_OMAP16XX,
  417. /* Either 12M from cam.mclk or 48M from dpll4 */
  418. .parent = &cam_mclk,
  419. };
  420. static struct clk cam_lclk = {
  421. .name = "cam.lclk",
  422. .flags = CLOCK_IN_OMAP310 | CLOCK_IN_OMAP1510 | CLOCK_IN_OMAP16XX,
  423. };
  424. static struct clk i2c_fck = {
  425. .name = "i2c_fck",
  426. .id = 1,
  427. .flags = CLOCK_IN_OMAP310 | CLOCK_IN_OMAP1510 | CLOCK_IN_OMAP16XX |
  428. ALWAYS_ENABLED,
  429. .parent = &armxor_ck,
  430. };
  431. static struct clk i2c_ick = {
  432. .name = "i2c_ick",
  433. .id = 1,
  434. .flags = CLOCK_IN_OMAP16XX | ALWAYS_ENABLED,
  435. .parent = &armper_ck,
  436. };
  437. static struct clk clk32k = {
  438. .name = "clk32-kHz",
  439. .flags = CLOCK_IN_OMAP310 | CLOCK_IN_OMAP1510 | CLOCK_IN_OMAP16XX |
  440. CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X | ALWAYS_ENABLED,
  441. .parent = &xtal_osc32k,
  442. };
  443. static struct clk ref_clk = {
  444. .name = "ref_clk",
  445. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X | ALWAYS_ENABLED,
  446. .rate = 12000000, /* 12 MHz or 13 MHz or 19.2 MHz */
  447. /*.parent = sys.xtalin */
  448. };
  449. static struct clk apll_96m = {
  450. .name = "apll_96m",
  451. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X | ALWAYS_ENABLED,
  452. .rate = 96000000,
  453. /*.parent = ref_clk */
  454. };
  455. static struct clk apll_54m = {
  456. .name = "apll_54m",
  457. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X | ALWAYS_ENABLED,
  458. .rate = 54000000,
  459. /*.parent = ref_clk */
  460. };
  461. static struct clk sys_clk = {
  462. .name = "sys_clk",
  463. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X | ALWAYS_ENABLED,
  464. .rate = 32768,
  465. /*.parent = sys.xtalin */
  466. };
  467. static struct clk sleep_clk = {
  468. .name = "sleep_clk",
  469. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X | ALWAYS_ENABLED,
  470. .rate = 32768,
  471. /*.parent = sys.xtalin */
  472. };
  473. static struct clk dpll_ck = {
  474. .name = "dpll",
  475. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X | ALWAYS_ENABLED,
  476. .parent = &ref_clk,
  477. };
  478. static struct clk dpll_x2_ck = {
  479. .name = "dpll_x2",
  480. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X | ALWAYS_ENABLED,
  481. .parent = &ref_clk,
  482. };
  483. static struct clk wdt1_sys_clk = {
  484. .name = "wdt1_sys_clk",
  485. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X | ALWAYS_ENABLED,
  486. .rate = 32768,
  487. /*.parent = sys.xtalin */
  488. };
  489. static struct clk func_96m_clk = {
  490. .name = "func_96m_clk",
  491. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  492. .divisor = 1,
  493. .parent = &apll_96m,
  494. };
  495. static struct clk func_48m_clk = {
  496. .name = "func_48m_clk",
  497. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  498. .divisor = 2,
  499. .parent = &apll_96m,
  500. };
  501. static struct clk func_12m_clk = {
  502. .name = "func_12m_clk",
  503. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  504. .divisor = 8,
  505. .parent = &apll_96m,
  506. };
  507. static struct clk func_54m_clk = {
  508. .name = "func_54m_clk",
  509. .flags = CLOCK_IN_OMAP242X,
  510. .divisor = 1,
  511. .parent = &apll_54m,
  512. };
  513. static struct clk sys_clkout = {
  514. .name = "clkout",
  515. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  516. .parent = &sys_clk,
  517. };
  518. static struct clk sys_clkout2 = {
  519. .name = "clkout2",
  520. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  521. .parent = &sys_clk,
  522. };
  523. static struct clk core_clk = {
  524. .name = "core_clk",
  525. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  526. .parent = &dpll_x2_ck, /* Switchable between dpll_ck and clk32k */
  527. };
  528. static struct clk l3_clk = {
  529. .name = "l3_clk",
  530. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  531. .parent = &core_clk,
  532. };
  533. static struct clk core_l4_iclk = {
  534. .name = "core_l4_iclk",
  535. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  536. .parent = &l3_clk,
  537. };
  538. static struct clk wu_l4_iclk = {
  539. .name = "wu_l4_iclk",
  540. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  541. .parent = &l3_clk,
  542. };
  543. static struct clk core_l3_iclk = {
  544. .name = "core_l3_iclk",
  545. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  546. .parent = &core_clk,
  547. };
  548. static struct clk core_l4_usb_clk = {
  549. .name = "core_l4_usb_clk",
  550. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  551. .parent = &l3_clk,
  552. };
  553. static struct clk wu_gpt1_clk = {
  554. .name = "wu_gpt1_clk",
  555. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  556. .parent = &sys_clk,
  557. };
  558. static struct clk wu_32k_clk = {
  559. .name = "wu_32k_clk",
  560. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  561. .parent = &sys_clk,
  562. };
  563. static struct clk uart1_fclk = {
  564. .name = "uart1_fclk",
  565. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  566. .parent = &func_48m_clk,
  567. };
  568. static struct clk uart1_iclk = {
  569. .name = "uart1_iclk",
  570. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  571. .parent = &core_l4_iclk,
  572. };
  573. static struct clk uart2_fclk = {
  574. .name = "uart2_fclk",
  575. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  576. .parent = &func_48m_clk,
  577. };
  578. static struct clk uart2_iclk = {
  579. .name = "uart2_iclk",
  580. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  581. .parent = &core_l4_iclk,
  582. };
  583. static struct clk uart3_fclk = {
  584. .name = "uart3_fclk",
  585. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  586. .parent = &func_48m_clk,
  587. };
  588. static struct clk uart3_iclk = {
  589. .name = "uart3_iclk",
  590. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  591. .parent = &core_l4_iclk,
  592. };
  593. static struct clk mpu_fclk = {
  594. .name = "mpu_fclk",
  595. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  596. .parent = &core_clk,
  597. };
  598. static struct clk mpu_iclk = {
  599. .name = "mpu_iclk",
  600. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  601. .parent = &core_clk,
  602. };
  603. static struct clk int_m_fclk = {
  604. .name = "int_m_fclk",
  605. .alias = "mpu_intc_fclk",
  606. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  607. .parent = &core_clk,
  608. };
  609. static struct clk int_m_iclk = {
  610. .name = "int_m_iclk",
  611. .alias = "mpu_intc_iclk",
  612. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  613. .parent = &core_clk,
  614. };
  615. static struct clk core_gpt2_clk = {
  616. .name = "core_gpt2_clk",
  617. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  618. .parent = &sys_clk,
  619. };
  620. static struct clk core_gpt3_clk = {
  621. .name = "core_gpt3_clk",
  622. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  623. .parent = &sys_clk,
  624. };
  625. static struct clk core_gpt4_clk = {
  626. .name = "core_gpt4_clk",
  627. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  628. .parent = &sys_clk,
  629. };
  630. static struct clk core_gpt5_clk = {
  631. .name = "core_gpt5_clk",
  632. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  633. .parent = &sys_clk,
  634. };
  635. static struct clk core_gpt6_clk = {
  636. .name = "core_gpt6_clk",
  637. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  638. .parent = &sys_clk,
  639. };
  640. static struct clk core_gpt7_clk = {
  641. .name = "core_gpt7_clk",
  642. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  643. .parent = &sys_clk,
  644. };
  645. static struct clk core_gpt8_clk = {
  646. .name = "core_gpt8_clk",
  647. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  648. .parent = &sys_clk,
  649. };
  650. static struct clk core_gpt9_clk = {
  651. .name = "core_gpt9_clk",
  652. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  653. .parent = &sys_clk,
  654. };
  655. static struct clk core_gpt10_clk = {
  656. .name = "core_gpt10_clk",
  657. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  658. .parent = &sys_clk,
  659. };
  660. static struct clk core_gpt11_clk = {
  661. .name = "core_gpt11_clk",
  662. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  663. .parent = &sys_clk,
  664. };
  665. static struct clk core_gpt12_clk = {
  666. .name = "core_gpt12_clk",
  667. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  668. .parent = &sys_clk,
  669. };
  670. static struct clk mcbsp1_clk = {
  671. .name = "mcbsp1_cg",
  672. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  673. .divisor = 2,
  674. .parent = &func_96m_clk,
  675. };
  676. static struct clk mcbsp2_clk = {
  677. .name = "mcbsp2_cg",
  678. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  679. .divisor = 2,
  680. .parent = &func_96m_clk,
  681. };
  682. static struct clk emul_clk = {
  683. .name = "emul_ck",
  684. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  685. .parent = &func_54m_clk,
  686. };
  687. static struct clk sdma_fclk = {
  688. .name = "sdma_fclk",
  689. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  690. .parent = &l3_clk,
  691. };
  692. static struct clk sdma_iclk = {
  693. .name = "sdma_iclk",
  694. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  695. .parent = &core_l3_iclk, /* core_l4_iclk for the configuration port */
  696. };
  697. static struct clk i2c1_fclk = {
  698. .name = "i2c1.fclk",
  699. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  700. .parent = &func_12m_clk,
  701. .divisor = 1,
  702. };
  703. static struct clk i2c1_iclk = {
  704. .name = "i2c1.iclk",
  705. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  706. .parent = &core_l4_iclk,
  707. };
  708. static struct clk i2c2_fclk = {
  709. .name = "i2c2.fclk",
  710. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  711. .parent = &func_12m_clk,
  712. .divisor = 1,
  713. };
  714. static struct clk i2c2_iclk = {
  715. .name = "i2c2.iclk",
  716. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  717. .parent = &core_l4_iclk,
  718. };
  719. static struct clk gpio_dbclk[4] = {
  720. {
  721. .name = "gpio1_dbclk",
  722. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  723. .parent = &wu_32k_clk,
  724. }, {
  725. .name = "gpio2_dbclk",
  726. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  727. .parent = &wu_32k_clk,
  728. }, {
  729. .name = "gpio3_dbclk",
  730. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  731. .parent = &wu_32k_clk,
  732. }, {
  733. .name = "gpio4_dbclk",
  734. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  735. .parent = &wu_32k_clk,
  736. },
  737. };
  738. static struct clk gpio_iclk = {
  739. .name = "gpio_iclk",
  740. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  741. .parent = &wu_l4_iclk,
  742. };
  743. static struct clk mmc_fck = {
  744. .name = "mmc_fclk",
  745. .flags = CLOCK_IN_OMAP242X,
  746. .parent = &func_96m_clk,
  747. };
  748. static struct clk mmc_ick = {
  749. .name = "mmc_iclk",
  750. .flags = CLOCK_IN_OMAP242X,
  751. .parent = &core_l4_iclk,
  752. };
  753. static struct clk spi_fclk[3] = {
  754. {
  755. .name = "spi1_fclk",
  756. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  757. .parent = &func_48m_clk,
  758. }, {
  759. .name = "spi2_fclk",
  760. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  761. .parent = &func_48m_clk,
  762. }, {
  763. .name = "spi3_fclk",
  764. .flags = CLOCK_IN_OMAP243X,
  765. .parent = &func_48m_clk,
  766. },
  767. };
  768. static struct clk dss_clk[2] = {
  769. {
  770. .name = "dss_clk1",
  771. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  772. .parent = &core_clk,
  773. }, {
  774. .name = "dss_clk2",
  775. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  776. .parent = &sys_clk,
  777. },
  778. };
  779. static struct clk dss_54m_clk = {
  780. .name = "dss_54m_clk",
  781. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  782. .parent = &func_54m_clk,
  783. };
  784. static struct clk dss_l3_iclk = {
  785. .name = "dss_l3_iclk",
  786. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  787. .parent = &core_l3_iclk,
  788. };
  789. static struct clk dss_l4_iclk = {
  790. .name = "dss_l4_iclk",
  791. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  792. .parent = &core_l4_iclk,
  793. };
  794. static struct clk spi_iclk[3] = {
  795. {
  796. .name = "spi1_iclk",
  797. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  798. .parent = &core_l4_iclk,
  799. }, {
  800. .name = "spi2_iclk",
  801. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  802. .parent = &core_l4_iclk,
  803. }, {
  804. .name = "spi3_iclk",
  805. .flags = CLOCK_IN_OMAP243X,
  806. .parent = &core_l4_iclk,
  807. },
  808. };
  809. static struct clk omapctrl_clk = {
  810. .name = "omapctrl_iclk",
  811. .flags = CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X,
  812. /* XXX Should be in WKUP domain */
  813. .parent = &core_l4_iclk,
  814. };
  815. static struct clk *onchip_clks[] = {
  816. /* OMAP 1 */
  817. /* non-ULPD clocks */
  818. &xtal_osc12m,
  819. &xtal_osc32k,
  820. &ck_ref,
  821. &dpll1,
  822. &dpll2,
  823. &dpll3,
  824. &dpll4,
  825. &apll,
  826. &ck_48m,
  827. /* CK_GEN1 clocks */
  828. &clkm1,
  829. &ck_dpll1out,
  830. &sossi_ck,
  831. &arm_ck,
  832. &armper_ck,
  833. &arm_gpio_ck,
  834. &armxor_ck,
  835. &armtim_ck,
  836. &armwdt_ck,
  837. &arminth_ck15xx, &arminth_ck16xx,
  838. /* CK_GEN2 clocks */
  839. &clkm2,
  840. &dsp_ck,
  841. &dspmmu_ck,
  842. &dspper_ck,
  843. &dspxor_ck,
  844. &dsptim_ck,
  845. /* CK_GEN3 clocks */
  846. &clkm3,
  847. &tc_ck,
  848. &tipb_ck,
  849. &l3_ocpi_ck,
  850. &tc1_ck,
  851. &tc2_ck,
  852. &dma_ck,
  853. &dma_lcdfree_ck,
  854. &api_ck,
  855. &lb_ck,
  856. &lbfree_ck,
  857. &hsab_ck,
  858. &rhea1_ck,
  859. &rhea2_ck,
  860. &lcd_ck_16xx,
  861. &lcd_ck_1510,
  862. /* ULPD clocks */
  863. &uart1_1510,
  864. &uart1_16xx,
  865. &uart2_ck,
  866. &uart3_1510,
  867. &uart3_16xx,
  868. &usb_clk0,
  869. &usb_hhc_ck1510, &usb_hhc_ck16xx,
  870. &mclk_1510, &mclk_16xx, &mclk_310,
  871. &bclk_1510, &bclk_16xx, &bclk_310,
  872. &mmc1_ck,
  873. &mmc2_ck,
  874. &cam_mclk,
  875. &cam_exclk,
  876. &cam_lclk,
  877. &clk32k,
  878. &usb_w2fc_mclk,
  879. /* Virtual clocks */
  880. &i2c_fck,
  881. &i2c_ick,
  882. /* OMAP 2 */
  883. &ref_clk,
  884. &apll_96m,
  885. &apll_54m,
  886. &sys_clk,
  887. &sleep_clk,
  888. &dpll_ck,
  889. &dpll_x2_ck,
  890. &wdt1_sys_clk,
  891. &func_96m_clk,
  892. &func_48m_clk,
  893. &func_12m_clk,
  894. &func_54m_clk,
  895. &sys_clkout,
  896. &sys_clkout2,
  897. &core_clk,
  898. &l3_clk,
  899. &core_l4_iclk,
  900. &wu_l4_iclk,
  901. &core_l3_iclk,
  902. &core_l4_usb_clk,
  903. &wu_gpt1_clk,
  904. &wu_32k_clk,
  905. &uart1_fclk,
  906. &uart1_iclk,
  907. &uart2_fclk,
  908. &uart2_iclk,
  909. &uart3_fclk,
  910. &uart3_iclk,
  911. &mpu_fclk,
  912. &mpu_iclk,
  913. &int_m_fclk,
  914. &int_m_iclk,
  915. &core_gpt2_clk,
  916. &core_gpt3_clk,
  917. &core_gpt4_clk,
  918. &core_gpt5_clk,
  919. &core_gpt6_clk,
  920. &core_gpt7_clk,
  921. &core_gpt8_clk,
  922. &core_gpt9_clk,
  923. &core_gpt10_clk,
  924. &core_gpt11_clk,
  925. &core_gpt12_clk,
  926. &mcbsp1_clk,
  927. &mcbsp2_clk,
  928. &emul_clk,
  929. &sdma_fclk,
  930. &sdma_iclk,
  931. &i2c1_fclk,
  932. &i2c1_iclk,
  933. &i2c2_fclk,
  934. &i2c2_iclk,
  935. &gpio_dbclk[0],
  936. &gpio_dbclk[1],
  937. &gpio_dbclk[2],
  938. &gpio_dbclk[3],
  939. &gpio_iclk,
  940. &mmc_fck,
  941. &mmc_ick,
  942. &spi_fclk[0],
  943. &spi_iclk[0],
  944. &spi_fclk[1],
  945. &spi_iclk[1],
  946. &spi_fclk[2],
  947. &spi_iclk[2],
  948. &dss_clk[0],
  949. &dss_clk[1],
  950. &dss_54m_clk,
  951. &dss_l3_iclk,
  952. &dss_l4_iclk,
  953. &omapctrl_clk,
  954. NULL
  955. };
  956. void omap_clk_adduser(struct clk *clk, qemu_irq user)
  957. {
  958. qemu_irq *i;
  959. for (i = clk->users; *i; i ++);
  960. *i = user;
  961. }
  962. struct clk *omap_findclk(struct omap_mpu_state_s *mpu, const char *name)
  963. {
  964. struct clk *i;
  965. for (i = mpu->clks; i->name; i ++)
  966. if (!strcmp(i->name, name) || (i->alias && !strcmp(i->alias, name)))
  967. return i;
  968. hw_error("%s: %s not found\n", __FUNCTION__, name);
  969. }
  970. void omap_clk_get(struct clk *clk)
  971. {
  972. clk->usecount ++;
  973. }
  974. void omap_clk_put(struct clk *clk)
  975. {
  976. if (!(clk->usecount --))
  977. hw_error("%s: %s is not in use\n", __FUNCTION__, clk->name);
  978. }
  979. static void omap_clk_update(struct clk *clk)
  980. {
  981. int parent, running;
  982. qemu_irq *user;
  983. struct clk *i;
  984. if (clk->parent)
  985. parent = clk->parent->running;
  986. else
  987. parent = 1;
  988. running = parent && (clk->enabled ||
  989. ((clk->flags & ALWAYS_ENABLED) && clk->usecount));
  990. if (clk->running != running) {
  991. clk->running = running;
  992. for (user = clk->users; *user; user ++)
  993. qemu_set_irq(*user, running);
  994. for (i = clk->child1; i; i = i->sibling)
  995. omap_clk_update(i);
  996. }
  997. }
  998. static void omap_clk_rate_update_full(struct clk *clk, unsigned long int rate,
  999. unsigned long int div, unsigned long int mult)
  1000. {
  1001. struct clk *i;
  1002. qemu_irq *user;
  1003. clk->rate = muldiv64(rate, mult, div);
  1004. if (clk->running)
  1005. for (user = clk->users; *user; user ++)
  1006. qemu_irq_raise(*user);
  1007. for (i = clk->child1; i; i = i->sibling)
  1008. omap_clk_rate_update_full(i, rate,
  1009. div * i->divisor, mult * i->multiplier);
  1010. }
  1011. static void omap_clk_rate_update(struct clk *clk)
  1012. {
  1013. struct clk *i;
  1014. unsigned long int div, mult = div = 1;
  1015. for (i = clk; i->parent; i = i->parent) {
  1016. div *= i->divisor;
  1017. mult *= i->multiplier;
  1018. }
  1019. omap_clk_rate_update_full(clk, i->rate, div, mult);
  1020. }
  1021. void omap_clk_reparent(struct clk *clk, struct clk *parent)
  1022. {
  1023. struct clk **p;
  1024. if (clk->parent) {
  1025. for (p = &clk->parent->child1; *p != clk; p = &(*p)->sibling);
  1026. *p = clk->sibling;
  1027. }
  1028. clk->parent = parent;
  1029. if (parent) {
  1030. clk->sibling = parent->child1;
  1031. parent->child1 = clk;
  1032. omap_clk_update(clk);
  1033. omap_clk_rate_update(clk);
  1034. } else
  1035. clk->sibling = NULL;
  1036. }
  1037. void omap_clk_onoff(struct clk *clk, int on)
  1038. {
  1039. clk->enabled = on;
  1040. omap_clk_update(clk);
  1041. }
  1042. void omap_clk_canidle(struct clk *clk, int can)
  1043. {
  1044. if (can)
  1045. omap_clk_put(clk);
  1046. else
  1047. omap_clk_get(clk);
  1048. }
  1049. void omap_clk_setrate(struct clk *clk, int divide, int multiply)
  1050. {
  1051. clk->divisor = divide;
  1052. clk->multiplier = multiply;
  1053. omap_clk_rate_update(clk);
  1054. }
  1055. int64_t omap_clk_getrate(omap_clk clk)
  1056. {
  1057. return clk->rate;
  1058. }
  1059. void omap_clk_init(struct omap_mpu_state_s *mpu)
  1060. {
  1061. struct clk **i, *j, *k;
  1062. int count;
  1063. int flag;
  1064. if (cpu_is_omap310(mpu))
  1065. flag = CLOCK_IN_OMAP310;
  1066. else if (cpu_is_omap1510(mpu))
  1067. flag = CLOCK_IN_OMAP1510;
  1068. else if (cpu_is_omap2410(mpu) || cpu_is_omap2420(mpu))
  1069. flag = CLOCK_IN_OMAP242X;
  1070. else if (cpu_is_omap2430(mpu))
  1071. flag = CLOCK_IN_OMAP243X;
  1072. else if (cpu_is_omap3430(mpu))
  1073. flag = CLOCK_IN_OMAP243X;
  1074. else
  1075. return;
  1076. for (i = onchip_clks, count = 0; *i; i ++)
  1077. if ((*i)->flags & flag)
  1078. count ++;
  1079. mpu->clks = (struct clk *) qemu_mallocz(sizeof(struct clk) * (count + 1));
  1080. for (i = onchip_clks, j = mpu->clks; *i; i ++)
  1081. if ((*i)->flags & flag) {
  1082. memcpy(j, *i, sizeof(struct clk));
  1083. for (k = mpu->clks; k < j; k ++)
  1084. if (j->parent && !strcmp(j->parent->name, k->name)) {
  1085. j->parent = k;
  1086. j->sibling = k->child1;
  1087. k->child1 = j;
  1088. } else if (k->parent && !strcmp(k->parent->name, j->name)) {
  1089. k->parent = j;
  1090. k->sibling = j->child1;
  1091. j->child1 = k;
  1092. }
  1093. j->divisor = j->divisor ?: 1;
  1094. j->multiplier = j->multiplier ?: 1;
  1095. j ++;
  1096. }
  1097. for (j = mpu->clks; count --; j ++) {
  1098. omap_clk_update(j);
  1099. omap_clk_rate_update(j);
  1100. }
  1101. }