@@ -1624,36 +1624,49 @@ int test_SerialNumber0_RootCA(void)
16241624 return EXPECT_RESULT ();
16251625}
16261626
1627- int test_wc_DecodeObjectId (void )
1627+
1628+ int test_wc_DecodeObjectId_FIPS16 (void )
16281629{
16291630 EXPECT_DECLS ;
16301631
16311632#if !defined(NO_ASN ) && \
16321633 (defined(HAVE_OID_DECODING ) || defined(WOLFSSL_ASN_PRINT ))
16331634 {
1634- /* OID 1.2.840.113549.1.1.11 (sha256WithRSAEncryption)
1635- * DER encoding: 2a 86 48 86 f7 0d 01 01 0b
1636- * First byte 0x2a = 42 => arc0 = 42/40 = 1, arc1 = 42%40 = 2
1637- * Remaining arcs: 840, 113549, 1, 1, 11
1635+ word32 i ;
1636+ static const word16 oid_dot_2 [] = {
1637+ 2 , 100 , 4 , 6
1638+ };
1639+
1640+ static const byte oid_start_with_2 [] = {
1641+ 0x81 , 0x34 , 0x04 , 0x06
1642+ };
1643+
1644+
1645+ /* OID 1.3.132.0.6 (secp112r1)
1646+ * DER encoding: 2b 81 04 00 06
1647+ * First byte 0x2b = 43 => arc0 = 43/40 = 1, arc1 = 43%40 = 3
1648+ * Remaining arcs: 132 0 6
16381649 */
16391650 static const byte oid_sha256rsa [] = {
1640- 0x2a , 0x86 , 0x48 , 0x86 , 0xf7 , 0x0d , 0x01 , 0x01 , 0x0b
1651+ 0x2B , 0x81 , 0x04 , 0x00 , 0x06
1652+ };
1653+
1654+ static const word16 oid_dot_form [] = {
1655+ 1U , 3U , 132U , 0U , 6U
16411656 };
1657+
16421658 word16 out [MAX_OID_SZ ];
16431659 word32 outSz ;
16441660
1661+ word32 trueOutSz = sizeof (oid_dot_form ) / sizeof (* oid_dot_form );
16451662 /* Test 1: Normal decode */
16461663 outSz = MAX_OID_SZ ;
16471664 ExpectIntEQ (DecodeObjectId (oid_sha256rsa , sizeof (oid_sha256rsa ),
16481665 out , & outSz ), 0 );
1649- ExpectIntEQ ((int )outSz , 7 );
1650- ExpectIntEQ (out [0 ], 1 );
1651- ExpectIntEQ (out [1 ], 2 );
1652- ExpectIntEQ (out [2 ], 840 );
1653- ExpectIntEQ (out [3 ], (word16 )113549 ); /* truncated to word16 */
1654- ExpectIntEQ (out [4 ], 1 );
1655- ExpectIntEQ (out [5 ], 1 );
1656- ExpectIntEQ (out [6 ], 11 );
1666+ ExpectIntEQ ((int )outSz , trueOutSz );
1667+ for (i = 0 ; i < ((outSz <= trueOutSz ) ? outSz : trueOutSz ); i ++ ) {
1668+ ExpectIntEQ (out [i ], oid_dot_form [i ]);
1669+ }
16571670
16581671 /* Test 2: NULL args */
16591672 outSz = MAX_OID_SZ ;
@@ -1692,12 +1705,251 @@ int test_wc_DecodeObjectId(void)
16921705 ExpectIntEQ (DecodeObjectId (oid_sha256rsa , sizeof (oid_sha256rsa ),
16931706 out , & outSz ),
16941707 WC_NO_ERR_TRACE (BUFFER_E ));
1708+
1709+ /* Test 7: first Arc is 2 */
1710+ {
1711+ word32 trueOutSz2 = sizeof (oid_dot_2 ) / sizeof (* oid_dot_2 );
1712+ outSz = MAX_OID_SZ ;
1713+ ExpectIntEQ (DecodeObjectId (oid_start_with_2 ,
1714+ sizeof (oid_start_with_2 ),
1715+ out , & outSz ), 0 );
1716+ ExpectIntEQ ((int )outSz , trueOutSz2 );
1717+ for (i = 0 ; i < ((outSz <= trueOutSz2 ) ?
1718+ outSz : trueOutSz2 ); i ++ ) {
1719+ ExpectIntEQ (out [i ], oid_dot_2 [i ]);
1720+ }
1721+ }
1722+
1723+ /* Test 8: an OID with an arc that exceeds word16. Tests that wrong
1724+ * but unchangable behavior is workign correctly,
1725+ *
1726+ * word16 version is used in FIPS build
1727+ */
1728+ {
1729+ static const byte oid_large_arc [] = {
1730+ 0x2a , 0x86 , 0x48 , 0x82 , 0xf7 , 0x0d , 0x01 , 0x01 , 0x0b
1731+ };
1732+ static const word16 oid_dot_large_arc [] = {
1733+ 1U , 2U , 840U , (word16 )113549U , 1U , 1U , 11U
1734+ };
1735+ word32 trueOutSz3 = sizeof (oid_dot_large_arc ) / sizeof (word16 );
1736+
1737+ outSz = MAX_OID_SZ ;
1738+ ExpectIntEQ (DecodeObjectId (oid_large_arc , sizeof (oid_large_arc ),
1739+ out , & outSz ), 0 );
1740+ ExpectIntEQ ((int )outSz , (int )trueOutSz3 );
1741+ for (i = 0 ; i < ((outSz <= trueOutSz3 ) ? outSz : trueOutSz3 ); i ++ ) {
1742+ ExpectIntEQ (out [i ], oid_dot_large_arc [i ]);
1743+ }
1744+ #undef LARGE_ARC_EXPECTED
1745+ }
16951746 }
16961747#endif /* !NO_ASN && (HAVE_OID_DECODING || WOLFSSL_ASN_PRINT) */
16971748
16981749 return EXPECT_RESULT ();
16991750}
17001751
1752+ /* Test for word16 FIPS version of function */
1753+ int test_wc_DecodeObjectId_ex (void )
1754+ {
1755+ EXPECT_DECLS ;
1756+
1757+ #if !defined(NO_ASN ) && \
1758+ (defined(HAVE_OID_DECODING ) || defined(WOLFSSL_ASN_PRINT ))
1759+ {
1760+ word32 i ;
1761+ static const word32 oid_dot_2 [] = {
1762+ 2 , 100 , 4 , 6
1763+ };
1764+
1765+ static const byte oid_start_with_2 [] = {
1766+ 0x81 , 0x34 , 0x04 , 0x06
1767+ };
1768+
1769+
1770+ /* OID 1.3.132.0.6 (secp112r1)
1771+ * DER encoding: 2b 81 04 00 06
1772+ * First byte 0x2b = 43 => arc0 = 43/40 = 1, arc1 = 43%40 = 3
1773+ * Remaining arcs: 132 0 6
1774+ */
1775+ static const byte oid_sha256rsa [] = {
1776+ 0x2B , 0x81 , 0x04 , 0x00 , 0x06
1777+ };
1778+
1779+ static const word32 oid_dot_form [] = {
1780+ 1U , 3U , 132U , 0U , 6U
1781+ };
1782+
1783+ word32 out [MAX_OID_SZ ];
1784+ word32 outSz ;
1785+
1786+ word32 trueOutSz = sizeof (oid_dot_form ) / sizeof (word32 );
1787+ /* Test 1: Normal decode */
1788+ outSz = MAX_OID_SZ ;
1789+ ExpectIntEQ (DecodeObjectId_ex (oid_sha256rsa , sizeof (oid_sha256rsa ),
1790+ out , & outSz ), 0 );
1791+ ExpectIntEQ ((int )outSz , trueOutSz );
1792+ for (i = 0 ; i < ((outSz <= trueOutSz ) ? outSz : trueOutSz ); i ++ ) {
1793+ ExpectIntEQ (out [i ], oid_dot_form [i ]);
1794+ }
1795+
1796+ /* Test 2: NULL args */
1797+ outSz = MAX_OID_SZ ;
1798+ ExpectIntEQ (DecodeObjectId_ex (NULL , sizeof (oid_sha256rsa ), out , & outSz ),
1799+ WC_NO_ERR_TRACE (BAD_FUNC_ARG ));
1800+ ExpectIntEQ (DecodeObjectId_ex (oid_sha256rsa , sizeof (oid_sha256rsa ),
1801+ out , NULL ),
1802+ WC_NO_ERR_TRACE (BAD_FUNC_ARG ));
1803+
1804+ /* Test 3 (Bug 1): outSz=1 must return BUFFER_E, not OOB write.
1805+ * The first OID byte decodes into two arcs, so outSz must be >= 2. */
1806+ outSz = 1 ;
1807+ ExpectIntEQ (DecodeObjectId_ex (oid_sha256rsa , sizeof (oid_sha256rsa ),
1808+ out , & outSz ),
1809+ WC_NO_ERR_TRACE (BUFFER_E ));
1810+
1811+ /* Test 4: outSz=0 must also return BUFFER_E */
1812+ outSz = 0 ;
1813+ ExpectIntEQ (DecodeObjectId_ex (oid_sha256rsa , sizeof (oid_sha256rsa ),
1814+ out , & outSz ),
1815+ WC_NO_ERR_TRACE (BUFFER_E ));
1816+
1817+ /* Test 5: outSz=2 is enough for a single-byte OID (two arcs) */
1818+ {
1819+ static const byte oid_one_byte [] = { 0x2a }; /* 1.2 */
1820+ outSz = 2 ;
1821+ ExpectIntEQ (DecodeObjectId_ex (oid_one_byte , sizeof (oid_one_byte ),
1822+ out , & outSz ), 0 );
1823+ ExpectIntEQ ((int )outSz , 2 );
1824+ ExpectIntEQ (out [0 ], 1 );
1825+ ExpectIntEQ (out [1 ], 2 );
1826+ }
1827+
1828+ /* Test 6: Buffer too small for later arcs */
1829+ outSz = 3 ; /* only room for 3 arcs, but OID has 7 */
1830+ ExpectIntEQ (DecodeObjectId_ex (oid_sha256rsa , sizeof (oid_sha256rsa ),
1831+ out , & outSz ),
1832+ WC_NO_ERR_TRACE (BUFFER_E ));
1833+
1834+ /* Test 7: first Arc is 2 */
1835+ {
1836+ word32 trueOutSz2 = sizeof (oid_dot_2 ) / sizeof (word32 );
1837+ outSz = MAX_OID_SZ ;
1838+ ExpectIntEQ (DecodeObjectId_ex (oid_start_with_2 ,
1839+ sizeof (oid_start_with_2 ),
1840+ out , & outSz ), 0 );
1841+ ExpectIntEQ ((int )outSz , trueOutSz2 );
1842+ for (i = 0 ; i < ((outSz <= trueOutSz2 ) ?
1843+ outSz : trueOutSz2 ); i ++ ) {
1844+ ExpectIntEQ (out [i ], oid_dot_2 [i ]);
1845+ }
1846+ }
1847+
1848+ /* Test 8: an OID with an arc that exceeds word16.
1849+ */
1850+ {
1851+ static const byte oid_large_arc [] = {
1852+ 0x2a , 0x86 , 0x48 , 0x86 , 0xf7 , 0x0d , 0x01 , 0x01 , 0x0b
1853+ };
1854+ static const word32 oid_dot_large_arc [] = {
1855+ 1U , 2U , 840U , 113549U , 1U , 1U , 11U
1856+ };
1857+ word32 trueOutSz3 = sizeof (oid_dot_large_arc ) / sizeof (word32 );
1858+
1859+ outSz = MAX_OID_SZ ;
1860+ ExpectIntEQ (DecodeObjectId_ex (oid_large_arc , sizeof (oid_large_arc ),
1861+ out , & outSz ), 0 );
1862+ ExpectIntEQ ((int )outSz , (int )trueOutSz3 );
1863+ for (i = 0 ; i < ((outSz <= trueOutSz3 ) ? outSz : trueOutSz3 ); i ++ ) {
1864+ ExpectIntEQ (out [i ], oid_dot_large_arc [i ]);
1865+ }
1866+ #undef LARGE_ARC_EXPECTED
1867+ }
1868+ }
1869+ #endif /* !NO_ASN && (HAVE_OID_DECODING || WOLFSSL_ASN_PRINT) */
1870+
1871+ return EXPECT_RESULT ();
1872+ }
1873+
1874+ int test_wc_EncodeObjectId (void )
1875+ {
1876+ EXPECT_DECLS ;
1877+ #if defined(HAVE_OID_ENCODING ) && !defined(NO_ASN )
1878+ {
1879+ /* 1.3.132.0.6 (secp112r1) -- every arc fits in word16, so this
1880+ * encodes identically in both build configs. */
1881+ static const word32 oid_small [] = { 1U , 3U , 132U , 0U , 6U };
1882+ static const byte oid_small_der [] = {
1883+ 0x2b , 0x81 , 0x04 , 0x00 , 0x06
1884+ };
1885+ const word32 oid_small_cnt = sizeof (oid_small ) / sizeof (word32 );
1886+ byte out [MAX_OID_SZ ];
1887+ word32 outSz ;
1888+ word32 i ;
1889+
1890+ /* Test 1: length-only query (out == NULL) */
1891+ outSz = 0 ;
1892+ ExpectIntEQ (wc_EncodeObjectId (oid_small , oid_small_cnt , NULL , & outSz ),
1893+ 0 );
1894+ ExpectIntEQ ((int )outSz , (int )sizeof (oid_small_der ));
1895+
1896+ /* Test 2: normal encode matches expected DER */
1897+ outSz = sizeof (out );
1898+ ExpectIntEQ (wc_EncodeObjectId (oid_small , oid_small_cnt , out , & outSz ), 0 );
1899+ ExpectIntEQ ((int )outSz , (int )sizeof (oid_small_der ));
1900+ for (i = 0 ; i < outSz && i < sizeof (oid_small_der ); i ++ ) {
1901+ ExpectIntEQ (out [i ], oid_small_der [i ]);
1902+ }
1903+
1904+ /* Test 3: NULL args */
1905+ outSz = sizeof (out );
1906+ ExpectIntEQ (wc_EncodeObjectId (NULL , oid_small_cnt , out , & outSz ),
1907+ WC_NO_ERR_TRACE (BAD_FUNC_ARG ));
1908+ ExpectIntEQ (wc_EncodeObjectId (oid_small , oid_small_cnt , out , NULL ),
1909+ WC_NO_ERR_TRACE (BAD_FUNC_ARG ));
1910+
1911+ /* Test 4: output buffer too small */
1912+ outSz = 1 ;
1913+ ExpectIntEQ (wc_EncodeObjectId (oid_small , oid_small_cnt , out , & outSz ),
1914+ WC_NO_ERR_TRACE (BUFFER_E ));
1915+
1916+ /* Test 5 ): an arc > word16 can only be represented in the
1917+ */
1918+ {
1919+ static const word32 oid_large [] = {
1920+ 1U , 2U , 840U , 113549U , 1U , 1U , 11U
1921+ };
1922+ static const byte oid_large_der [] = {
1923+ 0x2a , 0x86 , 0x48 , 0x86 , 0xf7 , 0x0d , 0x01 , 0x01 , 0x0b
1924+ };
1925+ const word32 oid_large_cnt = sizeof (oid_large ) / sizeof (word32 );
1926+
1927+ outSz = sizeof (out );
1928+ ExpectIntEQ (wc_EncodeObjectId (oid_large , oid_large_cnt , out , & outSz ),
1929+ 0 );
1930+ ExpectIntEQ ((int )outSz , (int )sizeof (oid_large_der ));
1931+ for (i = 0 ; i < outSz && i < sizeof (oid_large_der ); i ++ ) {
1932+ ExpectIntEQ (out [i ], oid_large_der [i ]);
1933+ }
1934+
1935+ #if defined(HAVE_OID_DECODING ) || defined(WOLFSSL_ASN_PRINT )
1936+ {
1937+ word32 dec [MAX_OID_SZ ];
1938+ word32 decSz = MAX_OID_SZ ;
1939+ ExpectIntEQ (DecodeObjectId_ex (out , outSz , dec , & decSz ), 0 );
1940+ ExpectIntEQ ((int )decSz , (int )oid_large_cnt );
1941+ for (i = 0 ; i < decSz && i < oid_large_cnt ; i ++ ) {
1942+ ExpectIntEQ (dec [i ], oid_large [i ]);
1943+ }
1944+ }
1945+ #endif /* HAVE_OID_DECODING || WOLFSSL_ASN_PRINT */
1946+ }
1947+ }
1948+ #endif /* HAVE_OID_ENCODING && !NO_ASN */
1949+
1950+ return EXPECT_RESULT ();
1951+ }
1952+
17011953#if defined(HAVE_PKCS8 ) && !defined(NO_ASN ) && \
17021954 (defined(WOLFSSL_TEST_CERT ) || defined(OPENSSL_EXTRA ) || \
17031955 defined(OPENSSL_EXTRA_X509_SMALL ) || defined(WOLFSSL_PUBLIC_ASN )) && \
0 commit comments