otlgpos.c 28 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980
  1. #include "otlgpos.h"
  2. #include "otlcommn.h"
  3. /* forward declaration */
  4. static OTL_ValidateFunc otl_gpos_validate_funcs[];
  5. /************************************************************************/
  6. /************************************************************************/
  7. /***** *****/
  8. /***** VALUE RECORDS *****/
  9. /***** *****/
  10. /************************************************************************/
  11. /************************************************************************/
  12. static OTL_UInt
  13. otl_value_length( OTL_UInt format )
  14. {
  15. FT_UInt count;
  16. count = (( format & 0xAA ) >> 1) + ( format & 0x55 );
  17. count = (( count & 0xCC ) >> 2) + ( count & 0x33 );
  18. count = (( count & 0xF0 ) >> 4) + ( count & 0x0F );
  19. return count;
  20. }
  21. static void
  22. otl_value_validate( OTL_Bytes table,
  23. OTL_Bytes pos_table,
  24. OTL_UInt format,
  25. OTL_Validator valid )
  26. {
  27. OTL_Bytes p = table;
  28. OTL_UInt count, device;
  29. if ( format >= 0x100U )
  30. OTL_INVALID_DATA;
  31. for ( count = 4; count > 0; count-- )
  32. {
  33. if ( format & 1 )
  34. {
  35. OTL_CHECK( 2 );
  36. p += 2;
  37. }
  38. format >>= 1;
  39. }
  40. for ( count = 4; count > 0; count-- )
  41. {
  42. if ( format & 1 )
  43. {
  44. OTL_CHECK( 2 );
  45. device = OTL_NEXT_USHORT( p );
  46. if ( device )
  47. otl_device_table_validate( pos_table + device, valid );
  48. }
  49. format >>= 1;
  50. }
  51. }
  52. /************************************************************************/
  53. /************************************************************************/
  54. /***** *****/
  55. /***** ANCHORS *****/
  56. /***** *****/
  57. /************************************************************************/
  58. /************************************************************************/
  59. static void
  60. otl_anchor_validate( OTL_Bytes table,
  61. OTL_Validator valid )
  62. {
  63. OTL_Bytes p = table;
  64. OTL_UInt format;
  65. OTL_CHECK( 6 );
  66. format = OTL_NEXT_USHORT( p );
  67. p += 4;
  68. switch ( format )
  69. {
  70. case 1:
  71. break;
  72. case 2:
  73. OTL_CHECK( 2 ); /* anchor point */
  74. break;
  75. case 3:
  76. {
  77. OTL_UInt x_device, y_device;
  78. OTL_CHECK( 4 );
  79. x_device = OTL_NEXT_USHORT( p );
  80. y_device = OTL_NEXT_USHORT( p );
  81. if ( x_device )
  82. otl_device_table_validate( table + x_device, valid );
  83. if ( y_device )
  84. otl_device_table_validate( table + y_device, valid );
  85. }
  86. break;
  87. default:
  88. OTL_INVALID_DATA;
  89. }
  90. }
  91. /************************************************************************/
  92. /************************************************************************/
  93. /***** *****/
  94. /***** MARK ARRAY *****/
  95. /***** *****/
  96. /************************************************************************/
  97. /************************************************************************/
  98. static void
  99. otl_mark_array_validate( OTL_Bytes table,
  100. OTL_Validator valid )
  101. {
  102. OTL_Bytes p = table;
  103. OTL_UInt count;
  104. OTL_CHECK( 2 );
  105. count = OTL_NEXT_USHORT( p );
  106. OTL_CHECK( count * 4 );
  107. for ( ; count > 0; count-- )
  108. {
  109. p += 2; /* ignore class index */
  110. otl_anchor_validate( table + OTL_NEXT_USHORT( p ), valid );
  111. }
  112. }
  113. /************************************************************************/
  114. /************************************************************************/
  115. /***** *****/
  116. /***** GPOS LOOKUP TYPE 1 *****/
  117. /***** *****/
  118. /************************************************************************/
  119. /************************************************************************/
  120. static void
  121. otl_gpos_lookup1_validate( OTL_Bytes table,
  122. OTL_Validator valid )
  123. {
  124. OTL_Bytes p = table;
  125. OTL_UInt format;
  126. OTL_CHECK( 2 );
  127. format = OTL_NEXT_USHORT( p );
  128. switch ( format )
  129. {
  130. case 1:
  131. {
  132. FT_UInt coverage, value_format;
  133. OTL_CHECK( 4 );
  134. coverage = OTL_NEXT_USHORT( p );
  135. value_format = OTL_NEXT_USHORT( p );
  136. otl_coverage_validate( table + coverage, valid );
  137. otl_value_validate( p, table, value_format, valid );
  138. }
  139. break;
  140. case 2:
  141. {
  142. FT_UInt coverage, value_format, count, len;
  143. OTL_CHECK( 6 );
  144. coverage = OTL_NEXT_USHORT( p );
  145. value_format = OTL_NEXT_USHORT( p );
  146. count = OTL_NEXT_USHORT( p );
  147. len = otl_value_length( value_format );
  148. otl_coverage_validate( table + coverage, valid );
  149. OTL_CHECK( count * len );
  150. for ( ; count > 0; count-- )
  151. {
  152. otl_value_validate( p, table, value_format, valid );
  153. p += len;
  154. }
  155. }
  156. break;
  157. default:
  158. OTL_INVALID_DATA;
  159. }
  160. }
  161. /************************************************************************/
  162. /************************************************************************/
  163. /***** *****/
  164. /***** GPOS LOOKUP TYPE 2 *****/
  165. /***** *****/
  166. /************************************************************************/
  167. /************************************************************************/
  168. static otl_gpos_pairset_validate( OTL_Bytes table,
  169. OTL_Bytes pos_table,
  170. OTL_UInt format1,
  171. OTL_UInt format2,
  172. OTL_Validator valid )
  173. {
  174. OTL_Bytes p = table;
  175. OTL_UInt len1, len2, count;
  176. OTL_CHECK( 2 );
  177. count = OTL_NEXT_USHORT( p );
  178. len1 = otl_value_length( format1 );
  179. len2 = otl_value_length( format2 );
  180. OTL_CHECK( count * (len1+len2+2) );
  181. for ( ; count > 0; count-- )
  182. {
  183. p += 2; /* ignore glyph id */
  184. otl_value_validate( p, pos_table, format1, valid );
  185. p += len1;
  186. otl_value_validate( p, pos_table, format2, valid );
  187. p += len2;
  188. }
  189. }
  190. static void
  191. otl_gpos_lookup2_validate( OTL_Bytes table,
  192. OTL_Validator valid )
  193. {
  194. OTL_Bytes p = table;
  195. OTL_UInt format;
  196. OTL_CHECK( 2 );
  197. format = OTL_NEXT_USHORT( p );
  198. switch (format)
  199. {
  200. case 1:
  201. {
  202. OTL_UInt coverage, value1, value2, count;
  203. OTL_CHECK( 8 );
  204. coverage = OTL_NEXT_USHORT( p );
  205. value1 = OTL_NEXT_USHORT( p );
  206. value2 = OTL_NEXT_USHORT( p );
  207. count = OTL_NEXT_USHORT( p );
  208. otl_coverage_validate( table + coverage, valid );
  209. OTL_CHECK( count*2 );
  210. for ( ; count > 0; count-- )
  211. {
  212. otl_gpos_pairset_validate( table + OTL_NEXT_USHORT( p ),
  213. table, value1, value2, valid );
  214. }
  215. }
  216. break;
  217. case 2:
  218. {
  219. OTL_UInt coverage, value1, value2, class1, class2, count1, count2;
  220. OTL_UInt len1, len2;
  221. OTL_CHECK( 14 );
  222. coverage = OTL_NEXT_USHORT( p );
  223. value1 = OTL_NEXT_USHORT( p );
  224. value2 = OTL_NEXT_USHORT( p );
  225. class1 = OTL_NEXT_USHORT( p );
  226. class2 = OTL_NEXT_USHORT( p );
  227. count1 = OTL_NEXT_USHORT( p );
  228. count2 = OTL_NEXT_USHORT( p );
  229. len1 = otl_value_length( value1 );
  230. len2 = otl_value_length( value2 );
  231. otl_coverage_validate( table + coverage, valid );
  232. OTL_CHECK( count1*count2*(len1+len2) );
  233. for ( ; count1 > 0; count1-- )
  234. {
  235. for ( ; count2 > 0; count2-- )
  236. {
  237. otl_value_validate( p, table, value1, valid );
  238. p += len1;
  239. otl_value_validate( p, table, value2, valid );
  240. p += len2;
  241. }
  242. }
  243. }
  244. break;
  245. default:
  246. OTL_INVALID_DATA;
  247. }
  248. }
  249. /************************************************************************/
  250. /************************************************************************/
  251. /***** *****/
  252. /***** GPOS LOOKUP TYPE 3 *****/
  253. /***** *****/
  254. /************************************************************************/
  255. /************************************************************************/
  256. static void
  257. otl_gpos_lookup3_validate( OTL_Bytes table,
  258. OTL_Valid valid )
  259. {
  260. OTL_Bytes p = table;
  261. OTL_UInt format;
  262. OTL_CHECK( 2 );
  263. format = OTL_NEXT_USHORT( p );
  264. switch (format)
  265. {
  266. case 1:
  267. {
  268. OTL_UInt coverage, count, anchor1, anchor2;
  269. OTL_CHECK( 4 );
  270. coverage = OTL_NEXT_USHORT( p );
  271. count = OTL_NEXT_USHORT( p );
  272. otl_coverage_validate( table + coverage, valid );
  273. OTL_CHECK( count*4 );
  274. for ( ; count > 0; count-- )
  275. {
  276. anchor1 = OTL_NEXT_USHORT( p );
  277. anchor2 = OTL_NEXT_USHORT( p );
  278. if ( anchor1 )
  279. otl_anchor_validate( table + anchor1, valid );
  280. if ( anchor2 )
  281. otl_anchor_validate( table + anchor2, valid );
  282. }
  283. }
  284. break;
  285. default:
  286. OTL_INVALID_DATA;
  287. }
  288. }
  289. /************************************************************************/
  290. /************************************************************************/
  291. /***** *****/
  292. /***** GPOS LOOKUP TYPE 4 *****/
  293. /***** *****/
  294. /************************************************************************/
  295. /************************************************************************/
  296. static void
  297. otl_base_array_validate( OTL_Bytes table,
  298. OTL_UInt class_count,
  299. OTL_Validator valid )
  300. {
  301. OTL_Bytes p = table;
  302. OTL_UInt count, count2;
  303. OTL_CHECK( 2 );
  304. count = OTL_NEXT_USHORT( p );
  305. OTL_CHECK( count*class_count*2 );
  306. for ( ; count > 0; count-- )
  307. for ( count2 = class_count; count2 > 0; count2-- )
  308. otl_anchor_validate( table + OTL_NEXT_USHORT( p ) );
  309. }
  310. static void
  311. otl_gpos_lookup4_validate( OTL_Bytes table,
  312. OTL_Valid valid )
  313. {
  314. OTL_Bytes p = table;
  315. OTL_UInt format;
  316. OTL_CHECK( 2 );
  317. format = OTL_NEXT_USHORT( p );
  318. switch (format)
  319. {
  320. case 1:
  321. {
  322. OTL_UInt mark_coverage, base_coverage, class_count;
  323. OTL_UInt mark_array, base_array;
  324. OTL_CHECK( 10 );
  325. mark_coverage = OTL_NEXT_USHORT( p );
  326. base_coverage = OTL_NEXT_USHORT( p );
  327. class_count = OTL_NEXT_USHORT( p );
  328. mark_array = OTL_NEXT_USHORT( p );
  329. base_array = OTL_NEXT_USHORT( p );
  330. otl_coverage_validate( table + mark_coverage, valid );
  331. otl_coverage_validate( table + base_coverage, valid );
  332. otl_mark_array_validate( table + mark_array, valid );
  333. otl_base_array_validate( table, class_count, valid );
  334. }
  335. break;
  336. default:
  337. OTL_INVALID_DATA;
  338. }
  339. }
  340. /************************************************************************/
  341. /************************************************************************/
  342. /***** *****/
  343. /***** GPOS LOOKUP TYPE 5 *****/
  344. /***** *****/
  345. /************************************************************************/
  346. /************************************************************************/
  347. static void
  348. otl_liga_attach_validate( OTL_Bytes table,
  349. OTL_UInt class_count,
  350. OTL_Validator valid )
  351. {
  352. OTL_Bytes p = table;
  353. OTL_UInt count, count2;
  354. OTL_CHECK( 2 );
  355. count = OTL_NEXT_USHORT( p );
  356. OTL_CHECK( count*class_count*2 );
  357. for ( ; count > 0; count-- )
  358. for ( count2 = class_count; class_count > 0; class_count-- )
  359. otl_anchor_validate( table + OTL_NEXT_USHORT( p ), valid );
  360. }
  361. static void
  362. otl_liga_array_validate( OTL_Bytes table,
  363. OTL_UInt class_count,
  364. OTL_Validator valid )
  365. {
  366. OTL_Bytes p = table;
  367. OTL_UInt count, count2;
  368. OTL_CHECK( 2 );
  369. count = OTL_NEXT_USHORT( p );
  370. OTL_CHECK( count*2 );
  371. for ( ; count > 0; count-- )
  372. otl_liga_attach_validate( table + OTL_NEXT_USHORT( p ), valid );
  373. }
  374. static void
  375. otl_gpos_lookup5_validate( OTL_Bytes table,
  376. OTL_Valid valid )
  377. {
  378. OTL_Bytes p = table;
  379. OTL_UInt format;
  380. OTL_CHECK( 2 );
  381. format = OTL_NEXT_USHORT( p );
  382. switch (format)
  383. {
  384. case 1:
  385. {
  386. OTL_UInt mark_coverage, lig_coverage, class_count;
  387. OTL_UInt mar_array, lig_array;
  388. OTL_CHECK( 10 );
  389. mark_coverage = OTL_NEXT_USHORT( p );
  390. liga_coverage = OTL_NEXT_USHORT( p );
  391. class_count = OTL_NEXT_USHORT( p );
  392. mark_array = OTL_NEXT_USHORT( p );
  393. liga_array = OTL_NEXT_USHORT( p );
  394. otl_coverage_validate( table + mark_coverage, valid );
  395. otl_coverage_validate( table + liga_coverage, valid );
  396. otl_mark_array_validate( table + mark_array, valid );
  397. otl_liga_array_validate( table + liga_array, class_count, valid );
  398. }
  399. break;
  400. default:
  401. OTL_INVALID_DATA;
  402. }
  403. }
  404. /************************************************************************/
  405. /************************************************************************/
  406. /***** *****/
  407. /***** GPOS LOOKUP TYPE 6 *****/
  408. /***** *****/
  409. /************************************************************************/
  410. /************************************************************************/
  411. static void
  412. otl_mark2_array_validate( OTL_Bytes table,
  413. OTL_UInt class_count,
  414. OTL_Validator valid )
  415. {
  416. OTL_Bytes p = table;
  417. OTL_UInt count, count2;
  418. OTL_CHECK( 2 );
  419. count = OTL_NEXT_USHORT( p );
  420. OTL_CHECK( count*class_count*2 );
  421. for ( ; count > 0; count-- )
  422. for ( count2 = class_count; class_count > 0; class_count-- )
  423. otl_anchor_validate( table + OTL_NEXT_USHORT( p ), valid );
  424. }
  425. static void
  426. otl_gpos_lookup6_validate( OTL_Bytes table,
  427. OTL_Valid valid )
  428. {
  429. OTL_Bytes p = table;
  430. OTL_UInt format;
  431. OTL_CHECK( 2 );
  432. format = OTL_NEXT_USHORT( p );
  433. switch (format)
  434. {
  435. case 1:
  436. {
  437. OTL_UInt coverage1, coverage2, class_count, array1, array2;
  438. OTL_CHECK( 10 );
  439. coverage1 = OTL_NEXT_USHORT( p );
  440. coverage2 = OTL_NEXT_USHORT( p );
  441. class_count = OTL_NEXT_USHORT( p );
  442. array1 = OTL_NEXT_USHORT( p );
  443. array2 = OTL_NEXT_USHORT( p );
  444. otl_coverage_validate( table + coverage1, valid );
  445. otl_coverage_validate( table + coverage2, valid );
  446. otl_mark_array_validate( table + array1, valid );
  447. otl_mark2_array_validate( table + array2, valid );
  448. }
  449. break;
  450. default:
  451. OTL_INVALID_DATA;
  452. }
  453. }
  454. /************************************************************************/
  455. /************************************************************************/
  456. /***** *****/
  457. /***** GPOS LOOKUP TYPE 7 *****/
  458. /***** *****/
  459. /************************************************************************/
  460. /************************************************************************/
  461. static void
  462. otl_pos_rule_validate( OTL_Bytes table,
  463. OTL_Validator valid )
  464. {
  465. OTL_Bytes p = table;
  466. OTL_UInt glyph_count, pos_count;
  467. OTL_CHECK( 4 );
  468. glyph_count = OTL_NEXT_USHORT( p );
  469. pos_count = OTL_NEXT_USHORT( p );
  470. if ( glyph_count == 0 )
  471. OTL_INVALID_DATA;
  472. OTL_CHECK( (glyph_count-1)*2 + pos_count*4 );
  473. /* XXX: check glyph indices and pos lookups */
  474. }
  475. static void
  476. otl_pos_rule_set_validate( OTL_Bytes table,
  477. OTL_Validator valid )
  478. {
  479. OTL_Bytes p = table;
  480. OTL_UInt count;
  481. OTL_CHECK( 2 );
  482. count = OTL_NEXT_USHORT( p );
  483. OTL_CHECK( count*2 );
  484. for ( ; count > 0; count-- )
  485. otl_pos_rule_validate( table + OTL_NEXT_USHORT(p), valid );
  486. }
  487. static void
  488. otl_pos_class_rule_validate( OTL_Bytes table,
  489. OTL_Validator valid )
  490. {
  491. OTL_Bytes p = table;
  492. OTL_UInt glyph_count, pos_count;
  493. OTL_CHECK( 4 );
  494. glyph_count = OTL_NEXT_USHORT( p );
  495. pos_count = OTL_NEXT_USHORT( p );
  496. if ( glyph_count == 0 )
  497. OTL_INVALID_DATA;
  498. OTL_CHECK( (glyph_count-1)*2 + pos_count*4 );
  499. /* XXX: check glyph indices and pos lookups */
  500. }
  501. static void
  502. otl_pos_class_set_validate( OTL_Bytes table,
  503. OTL_Validator valid )
  504. {
  505. OTL_Bytes p = table;
  506. OTL_UInt count;
  507. OTL_CHECK( 2 );
  508. count = OTL_NEXT_USHORT( p );
  509. OTL_CHECK( count*2 );
  510. for ( ; count > 0; count-- )
  511. otl_pos_rule_validate( table + OTL_NEXT_USHORT(p), valid );
  512. }
  513. static void
  514. otl_gpos_lookup7_validate( OTL_Bytes table,
  515. OTL_Validator valid )
  516. {
  517. OTL_Bytes p = table;
  518. OTL_UInt format;
  519. OTL_CHECK( 2 );
  520. format = OTL_NEXT_USHORT( p );
  521. switch (format)
  522. {
  523. case 1:
  524. {
  525. OTL_UInt coverage, count;
  526. OTL_CHECK( 4 );
  527. coverage = OTL_NEXT_USHORT( p );
  528. count = OTL_NEXT_USHORT( p );
  529. otl_coverage_validate( table + coverage, valid );
  530. OTL_CHECK( count*2 );
  531. for ( ; count > 0; count-- )
  532. otl_pos_rule_set_validate( table + OTL_NEXT_USHORT( p ), valid );
  533. }
  534. break;
  535. case 2:
  536. {
  537. OTL_UInt coverage, class_def, count;
  538. OTL_CHECK( 6 );
  539. coverage = OTL_NEXT_USHORT( p );
  540. class_def = OTL_NEXT_USHORT( p );
  541. count = OTL_NEXT_USHORT( p );
  542. otl_coverage_validate ( table + coverage, valid );
  543. otl_class_definition_validate( table + class_def, valid );
  544. OTL_CHECK( count*2 );
  545. for ( ; count > 0; count-- )
  546. otl_
  547. }
  548. break;
  549. case 3:
  550. {
  551. OTL_UInt glyph_count, pos_count;
  552. OTL_CHECK( 4 );
  553. glyph_count = OTL_NEXT_USHORT( p );
  554. pos_count = OTL_NEXT_USHORT( p );
  555. OTL_CHECK( glyph_count*2 + pos_count*4 );
  556. for ( ; glyph_count > 0; glyph_count )
  557. otl_coverage_validate( table + OTL_NEXT_USHORT( p ), valid );
  558. /* XXX: check pos lookups */
  559. }
  560. break;
  561. default:
  562. OTL_INVALID_DATA;
  563. }
  564. }
  565. /************************************************************************/
  566. /************************************************************************/
  567. /***** *****/
  568. /***** GPOS LOOKUP TYPE 8 *****/
  569. /***** *****/
  570. /************************************************************************/
  571. /************************************************************************/
  572. static void
  573. otl_chain_pos_rule_validate( OTL_Bytes table,
  574. OTL_Validator valid )
  575. {
  576. OTL_Bytes p = table;
  577. OTL_UInt back_count, input_count, ahead_count, pos_count;
  578. OTL_CHECK( 2 );
  579. back_count = OTL_NEXT_USHORT( p );
  580. OTL_CHECK( back_count*2 + 2 );
  581. p += back_count*2;
  582. input_count = OTL_NEXT_USHORT( p );
  583. if ( input_count == 0 )
  584. OTL_INVALID_DATA;
  585. OTL_CHECK( input_count*2 );
  586. p += (input_count-1)*2;
  587. ahead_count = OTL_NEXT_USHORT( p );
  588. OTL_CHECK( ahead_count*2 + 2 );
  589. p += ahead_count*2;
  590. pos_count = OTL_NEXT_USHORT( p );
  591. OTL_CHECK( pos_count*4 );
  592. }
  593. static void
  594. otl_chain_pos_rule_set_validate( OTL_Bytes table,
  595. OTL_Validator valid )
  596. {
  597. OTL_Bytes p = table;
  598. OTL_UInt count;
  599. OTL_CHECK( 2 );
  600. count = OTL_NEXT_USHORT( p );
  601. OTL_CHECK( 2*count );
  602. for ( ; count > 0; count-- )
  603. otl_chain_pos_rule_validate( table + OTL_NEXT_USHORT( p ), valid );
  604. }
  605. static void
  606. otl_chain_pos_class_rule_validate( OTL_Bytes table,
  607. OTL_Validator valid )
  608. {
  609. OTL_Bytes p = table;
  610. OTL_UInt back_count, input_count, ahead_count, pos_count;
  611. OTL_CHECK( 2 );
  612. back_count = OTL_NEXT_USHORT( p );
  613. OTL_CHECK( back_count*2 + 2 );
  614. p += back_count*2;
  615. input_count = OTL_NEXT_USHORT( p );
  616. if ( input_count == 0 )
  617. OTL_INVALID_DATA;
  618. OTL_CHECK( input_count*2 );
  619. p += (input_count-1)*2;
  620. ahead_count = OTL_NEXT_USHORT( p );
  621. OTL_CHECK( ahead_count*2 + 2 );
  622. p += ahead_count*2;
  623. pos_count = OTL_NEXT_USHORT( p );
  624. OTL_CHECK( pos_count*4 );
  625. }
  626. static void
  627. otl_chain_pos_class_set_validate( OTL_Bytes table,
  628. OTL_Validator valid )
  629. {
  630. OTL_Bytes p = table;
  631. OTL_UInt count;
  632. OTL_CHECK( 2 );
  633. count = OTL_NEXT_USHORT( p );
  634. OTL_CHECK( 2*count );
  635. for ( ; count > 0; count-- )
  636. otl_chain_pos_class_rule_validate( table + OTL_NEXT_USHORT( p ), valid );
  637. }
  638. static void
  639. otl_gpos_lookup8_validate( OTL_Bytes table,
  640. OTL_Validator valid )
  641. {
  642. OTL_Bytes p = table;
  643. OTL_UInt format;
  644. OTL_CHECK( 2 );
  645. format = OTL_NEXT_USHORT( p );
  646. switch (format)
  647. {
  648. case 1:
  649. {
  650. OTL_UInt coverage, count;
  651. OTL_CHECK( 4 );
  652. coverage = OTL_NEXT_USHORT( p );
  653. count = OTL_NEXT_USHORT( p );
  654. otl_coverage_validate( table + coverage, valid );
  655. OTL_CHECK( count*2 );
  656. for ( ; count > 0; count-- )
  657. otl_chain_pos_rule_set_validate( table + OTL_NEXT_USHORT( p ),
  658. valid );
  659. }
  660. break;
  661. case 2:
  662. {
  663. OTL_UInt coverage, back_class, input_class, ahead_class, count;
  664. OTL_CHECK( 10 );
  665. coverage = OTL_NEXT_USHORT( p );
  666. back_class = OTL_NEXT_USHORT( p );
  667. input_class = OTL_NEXT_USHORT( p );
  668. ahead_class = OTL_NEXT_USHORT( p );
  669. count = OTL_NEXT_USHORT( p );
  670. otl_coverage_validate( table + coverage, valid );
  671. otl_class_definition_validate( table + back_class, valid );
  672. otl_class_definition_validate( table + input_class, valid );
  673. otl_class_definition_validate( table + ahead_class, valid );
  674. OTL_CHECK( count*2 );
  675. for ( ; count > 0; count-- )
  676. otl_chain_pos_class_set_validate( table + OTL_NEXT_USHORT( p ),
  677. valid );
  678. }
  679. break;
  680. case 3:
  681. {
  682. OTL_UInt back_count, input_count, ahead_count, pos_count, count;
  683. OTL_CHECK( 2 );
  684. back_count = OTL_NEXT_USHORT( p );
  685. OTL_CHECK( 2*back_count+2 );
  686. for ( count = back_count; count > 0; count-- )
  687. otl_coverage_validate( table + OTL_NEXT_USHORT( p ), valid );
  688. input_count = OTL_NEXT_USHORT( p );
  689. OTL_CHECK( 2*input_count+2 );
  690. for ( count = input_count; count > 0; count-- )
  691. otl_coverage_validate( table + OTL_NEXT_USHORT( p ), valid );
  692. ahead_count = OTL_NEXT_USHORT( p );
  693. OTL_CHECK( 2*ahead_count+2 );
  694. for ( count = ahead_count; count > 0; count-- )
  695. otl_coverage_validate( table + OTL_NEXT_USHORT( p ), valid );
  696. pos_count = OTL_NEXT_USHORT( p );
  697. OTL_CHECK( pos_count*4 );
  698. }
  699. break;
  700. default:
  701. OTL_INVALID_DATA;
  702. }
  703. }
  704. /************************************************************************/
  705. /************************************************************************/
  706. /***** *****/
  707. /***** GPOS LOOKUP TYPE 9 *****/
  708. /***** *****/
  709. /************************************************************************/
  710. /************************************************************************/
  711. static void
  712. otl_gpos_lookup9_validate( OTL_Bytes table,
  713. OTL_Valid valid )
  714. {
  715. OTL_Bytes p = table;
  716. OTL_UInt format;
  717. OTL_CHECK( 2 );
  718. format = OTL_NEXT_USHORT( p );
  719. switch (format)
  720. {
  721. case 1:
  722. {
  723. OTL_UInt lookup_type, lookup_offset;
  724. OTL_ValidateFunc validate;
  725. OTL_CHECK( 6 );
  726. lookup_type = OTL_NEXT_USHORT( p );
  727. lookup_offset = OTL_NEXT_ULONG( p );
  728. if ( lookup_type == 0 || lookup_type >= 9 )
  729. OTL_INVALID_DATA;
  730. validate = otl_gpos_validate_funcs[ lookup_type-1 ];
  731. validate( table + lookup_offset, valid );
  732. }
  733. break;
  734. default:
  735. OTL_INVALID_DATA;
  736. }
  737. }
  738. static OTL_ValidateFunc otl_gpos_validate_funcs[ 9 ] =
  739. {
  740. otl_gpos_lookup1_validate,
  741. otl_gpos_lookup2_validate,
  742. otl_gpos_lookup3_validate,
  743. otl_gpos_lookup4_validate,
  744. otl_gpos_lookup5_validate,
  745. otl_gpos_lookup6_validate,
  746. otl_gpos_lookup7_validate,
  747. otl_gpos_lookup8_validate,
  748. otl_gpos_lookup9_validate,
  749. };
  750. /************************************************************************/
  751. /************************************************************************/
  752. /***** *****/
  753. /***** GPOS TABLE *****/
  754. /***** *****/
  755. /************************************************************************/
  756. /************************************************************************/
  757. OTL_LOCALDEF( void )
  758. otl_gpos_validate( OTL_Bytes table,
  759. OTL_Validator valid )
  760. {
  761. OTL_Bytes p = table;
  762. OTL_UInt scripts, features, lookups;
  763. OTL_CHECK( 10 );
  764. if ( OTL_NEXT_USHORT( p ) != 0x10000UL )
  765. OTL_INVALID_DATA;
  766. scripts = OTL_NEXT_USHORT( p );
  767. features = OTL_NEXT_USHORT( p );
  768. lookups = OTL_NEXT_USHORT( p );
  769. otl_script_list_validate ( table + scripts, valid );
  770. otl_feature_list_validate( table + features, valid );
  771. otl_lookup_list_validate( table + lookups, 9, otl_gpos_validate_funcs,
  772. valid );
  773. }