Source code of Windows XP (NT5)
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

1365 lines
24 KiB

  1. /*++
  2. Copyright (c) 1992-2000 Microsoft Corporation
  3. Module Name:
  4. wstring.hxx
  5. Abstract:
  6. This module defines the new WSTRING hierarchy:
  7. WSTRING
  8. FSTRING
  9. DSTRING
  10. WSTRING provides all of the desired methods on a string.
  11. FSTRING provides an implementation of a WSTRING with fixed
  12. size, user provided buffer.
  13. DSTRING provides an implementation of a WSTRING with a
  14. dynamic heap based buffer.
  15. WSTRING is an abstract classes who's methods depend on the
  16. implementation of two pure virtual methods: 'Resize' and 'NewBuf'.
  17. A derived class must make use of the protected 'PutString' methods
  18. in order to supply WSTRING with its string buffer. Use of
  19. 'PutString' is constrained as follows:
  20. 1. Supplying just a PWSTR to 'PutString' implies that
  21. the PWSTR is null-terminated.
  22. 2. Supplying a PWSTR and length to 'PutString' implies that
  23. the PWSTR points to a buffer of characters that is at
  24. least one longer than the given length.
  25. All implementations of 'Resize' and 'NewBuf' must:
  26. 1. Allocate an extra character for the NULL.
  27. 2. NULL-terminate the buffer allocated.
  28. 3. Always succeed if size <= current buffer size.
  29. 4. Always work as soon as the derived class is initialized (i.e.
  30. WSTRING::Initialize method need not be called.).
  31. 5. Supply the buffer to WSTRING via 'PutString'.
  32. Additionally 'Resize' must:
  33. 1. Preserve the contents of the current buffer.
  34. All of the comparison operators supplied by WSTRING are
  35. case insensitive.
  36. --*/
  37. #if !defined(_WSTRING_DEFN_)
  38. #define _WSTRING_DEFN_
  39. //
  40. // The type of the index used to access individual characters within
  41. // a generic string.
  42. //
  43. DEFINE_TYPE( ULONG, CHNUM );
  44. //
  45. // Magic constants
  46. //
  47. #define INVALID_CHAR ((WCHAR)-1)
  48. #define INVALID_CHNUM ((CHNUM)-1)
  49. #define TO_END INVALID_CHNUM
  50. //
  51. // Prefixes used in various names.
  52. // (This should really be in path.hxx.)
  53. //
  54. #define GUID_VOLNAME_PREFIX L"Volume{"
  55. #define DOS_GUIDNAME_PREFIX L"\\\\?\\"
  56. #define NT_NAME_PREFIX L"\\??\\"
  57. DECLARE_CLASS( WSTRING );
  58. class ULIB_EXPORT WSTRING : public OBJECT {
  59. public:
  60. NONVIRTUAL
  61. BOOLEAN
  62. Initialize(
  63. IN PCWSTRING InitialString,
  64. IN CHNUM Position DEFAULT 0,
  65. IN CHNUM Length DEFAULT TO_END
  66. );
  67. NONVIRTUAL
  68. BOOLEAN
  69. Initialize(
  70. IN PCWSTR InitialString,
  71. IN CHNUM StringLength DEFAULT TO_END
  72. );
  73. NONVIRTUAL
  74. BOOLEAN
  75. Initialize(
  76. IN PCSTR InitialString,
  77. IN CHNUM StringLength DEFAULT TO_END
  78. );
  79. NONVIRTUAL
  80. BOOLEAN
  81. Initialize(
  82. );
  83. NONVIRTUAL
  84. BOOLEAN
  85. Initialize(
  86. IN LONG Number
  87. );
  88. NONVIRTUAL
  89. PWSTRING
  90. QueryString(
  91. IN CHNUM Position DEFAULT 0,
  92. IN CHNUM Length DEFAULT TO_END
  93. ) CONST;
  94. NONVIRTUAL
  95. BOOLEAN
  96. QueryNumber(
  97. OUT PLONG Number,
  98. IN CHNUM Position DEFAULT 0,
  99. IN CHNUM Length DEFAULT TO_END
  100. ) CONST;
  101. NONVIRTUAL
  102. CHNUM
  103. QueryChCount(
  104. ) CONST;
  105. #ifdef FE_SB
  106. NONVIRTUAL
  107. CHNUM
  108. QueryByteCount(
  109. ) CONST;
  110. #endif
  111. NONVIRTUAL
  112. CHNUM
  113. SyncLength(
  114. );
  115. NONVIRTUAL
  116. WCHAR
  117. QueryChAt(
  118. IN CHNUM Position
  119. ) CONST;
  120. NONVIRTUAL
  121. WCHAR
  122. SetChAt(
  123. IN WCHAR Char,
  124. IN CHNUM Position
  125. );
  126. NONVIRTUAL
  127. VOID
  128. DeleteChAt(
  129. IN CHNUM Position,
  130. IN CHNUM Length DEFAULT 1
  131. );
  132. NONVIRTUAL
  133. BOOLEAN
  134. InsertString(
  135. IN CHNUM AtPosition,
  136. IN PCWSTRING String,
  137. IN CHNUM FromPosition DEFAULT 0,
  138. IN CHNUM FromLength DEFAULT TO_END
  139. );
  140. NONVIRTUAL
  141. BOOLEAN
  142. Replace(
  143. IN CHNUM AtPosition,
  144. IN CHNUM AtLength,
  145. IN PCWSTRING String,
  146. IN CHNUM FromPosition DEFAULT 0,
  147. IN CHNUM FromLength DEFAULT TO_END
  148. );
  149. NONVIRTUAL
  150. BOOLEAN
  151. ReplaceWithChars(
  152. IN CHNUM AtPosition,
  153. IN CHNUM AtLength,
  154. IN WCHAR Character,
  155. IN CHNUM FromLength
  156. );
  157. NONVIRTUAL
  158. PCWSTR
  159. GetWSTR(
  160. ) CONST;
  161. NONVIRTUAL
  162. PWSTR
  163. QueryWSTR(
  164. IN CHNUM Position DEFAULT 0,
  165. IN CHNUM Length DEFAULT TO_END,
  166. OUT PWSTR Buffer DEFAULT NULL,
  167. IN CHNUM BufferLength DEFAULT 0,
  168. IN BOOLEAN ForceNull DEFAULT TRUE
  169. ) CONST;
  170. NONVIRTUAL
  171. PSTR
  172. QuerySTR(
  173. IN CHNUM Position DEFAULT 0,
  174. IN CHNUM Length DEFAULT TO_END,
  175. OUT PSTR Buffer DEFAULT NULL,
  176. IN CHNUM BufferLength DEFAULT 0,
  177. IN BOOLEAN ForceNull DEFAULT TRUE
  178. ) CONST;
  179. NONVIRTUAL
  180. LONG
  181. Strcmp(
  182. IN PCWSTRING String
  183. ) CONST;
  184. STATIC
  185. INT
  186. Strcmp(
  187. IN PWSTR String1,
  188. IN PWSTR String2
  189. ) ;
  190. STATIC
  191. INT
  192. Stricmp(
  193. IN PWSTR String1,
  194. IN PWSTR String2
  195. ) ;
  196. NONVIRTUAL
  197. LONG
  198. Strcmp(
  199. IN PCWSTRING String,
  200. IN CHNUM LeftPosition
  201. ) CONST;
  202. NONVIRTUAL
  203. LONG
  204. Strcmp(
  205. IN PCWSTRING String,
  206. IN CHNUM LeftPosition,
  207. IN CHNUM LeftLength,
  208. IN CHNUM RightPosition DEFAULT 0,
  209. IN CHNUM RightLength DEFAULT TO_END
  210. ) CONST;
  211. NONVIRTUAL
  212. LONG
  213. Stricmp(
  214. IN PCWSTRING String
  215. ) CONST;
  216. NONVIRTUAL
  217. LONG
  218. Stricmp(
  219. IN PCWSTRING String,
  220. IN CHNUM LeftPosition
  221. ) CONST;
  222. NONVIRTUAL
  223. LONG
  224. Stricmp(
  225. IN PCWSTRING String,
  226. IN CHNUM LeftPosition,
  227. IN CHNUM LeftLength,
  228. IN CHNUM RightPosition DEFAULT 0,
  229. IN CHNUM RightLength DEFAULT TO_END
  230. ) CONST;
  231. STATIC
  232. INT
  233. Strcmps(
  234. IN PWSTR p1,
  235. IN PWSTR p2
  236. );
  237. STATIC
  238. INT
  239. Strcmpis(
  240. IN PWSTR p1,
  241. IN PWSTR p2
  242. );
  243. STATIC
  244. PWSTR
  245. SkipWhite(
  246. IN PWSTR p
  247. );
  248. NONVIRTUAL
  249. BOOLEAN
  250. Strcat(
  251. IN PCWSTRING String
  252. );
  253. NONVIRTUAL
  254. PWSTRING
  255. Strupr(
  256. );
  257. NONVIRTUAL
  258. PWSTRING
  259. Strupr(
  260. IN CHNUM StartPosition,
  261. IN CHNUM Length DEFAULT TO_END
  262. );
  263. NONVIRTUAL
  264. PWSTRING
  265. Strlwr(
  266. );
  267. NONVIRTUAL
  268. PWSTRING
  269. Strlwr(
  270. IN CHNUM StartPosition,
  271. IN CHNUM Length DEFAULT TO_END
  272. );
  273. NONVIRTUAL
  274. CHNUM
  275. Strchr(
  276. IN WCHAR Char,
  277. IN CHNUM StartPosition DEFAULT 0
  278. ) CONST;
  279. NONVIRTUAL
  280. CHNUM
  281. Strrchr(
  282. IN WCHAR Char,
  283. IN CHNUM StartPosition DEFAULT 0
  284. ) CONST;
  285. NONVIRTUAL
  286. CHNUM
  287. Strstr(
  288. IN PCWSTRING String
  289. ) CONST;
  290. NONVIRTUAL
  291. CHNUM
  292. Strspn(
  293. IN PCWSTRING String,
  294. IN CHNUM StartPosition DEFAULT 0
  295. ) CONST;
  296. NONVIRTUAL
  297. CHNUM
  298. Strcspn(
  299. IN PCWSTRING String,
  300. IN CHNUM StartPosition DEFAULT 0
  301. ) CONST;
  302. NONVIRTUAL
  303. BOOLEAN
  304. operator==(
  305. IN RCWSTRING String
  306. ) CONST;
  307. NONVIRTUAL
  308. BOOLEAN
  309. operator!=(
  310. IN RCWSTRING String
  311. ) CONST;
  312. NONVIRTUAL
  313. BOOLEAN
  314. operator<(
  315. IN RCWSTRING String
  316. ) CONST;
  317. NONVIRTUAL
  318. BOOLEAN
  319. operator>(
  320. IN RCWSTRING String
  321. ) CONST;
  322. NONVIRTUAL
  323. BOOLEAN
  324. operator<=(
  325. IN RCWSTRING String
  326. ) CONST;
  327. NONVIRTUAL
  328. BOOLEAN
  329. operator>=(
  330. IN RCWSTRING String
  331. ) CONST;
  332. VIRTUAL
  333. BOOLEAN
  334. Resize(
  335. IN CHNUM NewStringLength
  336. ) PURE;
  337. VIRTUAL
  338. BOOLEAN
  339. NewBuf(
  340. IN CHNUM NewStringLength
  341. ) PURE;
  342. NONVIRTUAL
  343. CHNUM
  344. Truncate(
  345. IN CHNUM Position DEFAULT 0
  346. );
  347. STATIC
  348. VOID
  349. SetAnsiConversions(
  350. );
  351. STATIC
  352. VOID
  353. SetOemConversions(
  354. );
  355. STATIC
  356. VOID
  357. SetConsoleConversions(
  358. );
  359. #if defined FE_SB
  360. STATIC
  361. VOID
  362. ResetConversions(
  363. );
  364. #endif
  365. protected:
  366. DECLARE_CONSTRUCTOR( WSTRING );
  367. NONVIRTUAL
  368. VOID
  369. Construct(
  370. );
  371. NONVIRTUAL
  372. VOID
  373. PutString(
  374. IN OUT PWSTR String
  375. );
  376. NONVIRTUAL
  377. VOID
  378. PutString(
  379. IN OUT PWSTR String,
  380. IN CHNUM Length
  381. );
  382. private:
  383. STATIC BOOLEAN _UseAnsiConversions;
  384. STATIC BOOLEAN _UseConsoleConversions;
  385. #if defined FE_SB
  386. STATIC BOOLEAN _UseAnsiConversionsPrev;
  387. STATIC BOOLEAN _UseConsoleConversionsPrev;
  388. #endif
  389. #if defined FE_SB
  390. STATIC
  391. INT
  392. CheckSpace(
  393. IN PWSTR p
  394. );
  395. #endif
  396. STATIC
  397. BOOLEAN
  398. ConvertOemToUnicodeN(
  399. PWSTR UnicodeString,
  400. ULONG MaxBytesInUnicodeString,
  401. PULONG BytesInUnicodeString,
  402. PCHAR OemString,
  403. ULONG BytesInOemString
  404. );
  405. STATIC
  406. BOOLEAN
  407. ConvertUnicodeToOemN(
  408. PCHAR OemString,
  409. ULONG MaxBytesInOemString,
  410. PULONG BytesInOemString,
  411. PWSTR UnicodeString,
  412. ULONG BytesInUnicodeString
  413. );
  414. PWSTR _s; // Beginning of string.
  415. CHNUM _l; // Strlen of string.
  416. };
  417. INLINE
  418. VOID
  419. WSTRING::PutString(
  420. IN OUT PWSTR String
  421. )
  422. /*++
  423. Routine Description:
  424. This routine initializes this string with the given null
  425. terminated buffer.
  426. Arguments:
  427. String - Supplies the buffer to initialize the string with.
  428. Return Value:
  429. None.
  430. --*/
  431. {
  432. _s = String;
  433. _l = wcslen(_s);
  434. }
  435. INLINE
  436. VOID
  437. WSTRING::PutString(
  438. IN OUT PWSTR String,
  439. IN CHNUM Length
  440. )
  441. /*++
  442. Routine Description:
  443. This routine initializes this string with the given buffer
  444. and string length.
  445. Arguments:
  446. String - Supplies the buffer to initialize the string with.
  447. Length - Supplies the length of the string.
  448. Return Value:
  449. None.
  450. --*/
  451. {
  452. _s = String;
  453. _l = Length;
  454. _s[_l] = 0;
  455. }
  456. INLINE
  457. BOOLEAN
  458. WSTRING::Initialize(
  459. )
  460. /*++
  461. Routine Description:
  462. This routine initializes this string to an empty null-terminated
  463. string.
  464. Arguments:
  465. None.
  466. Return Value:
  467. FALSE - Failure.
  468. TRUE - Success.
  469. --*/
  470. {
  471. return Resize(0);
  472. }
  473. INLINE
  474. CHNUM
  475. WSTRING::QueryChCount(
  476. ) CONST
  477. /*++
  478. Routine Description:
  479. This routine returns the number of characters in the string.
  480. Arguments:
  481. None.
  482. Return Value:
  483. The number of characters in this string.
  484. --*/
  485. {
  486. return _l;
  487. }
  488. INLINE
  489. CHNUM
  490. WSTRING::SyncLength(
  491. )
  492. /*++
  493. Routine Description:
  494. This routine recalculates the correct length of the string.
  495. Arguments:
  496. None.
  497. Return Value:
  498. The recomputed length of the string.
  499. --*/
  500. {
  501. return _l = wcslen(_s);
  502. }
  503. INLINE
  504. WCHAR
  505. WSTRING::QueryChAt(
  506. IN CHNUM Position
  507. ) CONST
  508. /*++
  509. Routine Description:
  510. This routine returns the character at the given position.
  511. The position is a zero-based index into the string.
  512. The position must be in the range of the string.
  513. Arguments:
  514. Position - Supplies an index into the string.
  515. Return Value:
  516. The character at the given position.
  517. --*/
  518. {
  519. return (Position < _l) ? _s[Position] : INVALID_CHAR;
  520. }
  521. INLINE
  522. WCHAR
  523. WSTRING::SetChAt(
  524. IN WCHAR Char,
  525. IN CHNUM Position
  526. )
  527. /*++
  528. Routine Description:
  529. This routine sets the given character at the given position in
  530. the string.
  531. Arguments:
  532. Char - Supplies the character to set into the string.
  533. Position - Supplies the position at which to set the character.
  534. Return Value:
  535. The character that was set.
  536. --*/
  537. {
  538. DebugAssert(Position < _l);
  539. return _s[Position] = Char;
  540. }
  541. INLINE
  542. PCWSTR
  543. WSTRING::GetWSTR(
  544. ) CONST
  545. /*++
  546. Routine Description:
  547. This routine returns this string internal buffer.
  548. Arguments:
  549. None.
  550. Return Value:
  551. A pointer to the strings buffer.
  552. --*/
  553. {
  554. return _s;
  555. }
  556. INLINE
  557. LONG
  558. WSTRING::Strcmp(
  559. IN PCWSTRING String
  560. ) CONST
  561. /*++
  562. Routine Description:
  563. This routine compares two strings.
  564. Arguments:
  565. String - Supplies the string to compare to.
  566. Return Value:
  567. < 0 - This string is less than the given string.
  568. 0 - This string is equal to the given string.
  569. > 0 - This string is greater than the given string.
  570. --*/
  571. {
  572. return wcscmp(_s, String->_s);
  573. }
  574. INLINE
  575. INT
  576. WSTRING::Strcmp(
  577. IN PWSTR String1,
  578. IN PWSTR String2
  579. )
  580. {
  581. return wcscmp( String1, String2 );
  582. }
  583. INLINE
  584. INT
  585. WSTRING::Stricmp(
  586. IN PWSTR String1,
  587. IN PWSTR String2
  588. )
  589. {
  590. return _wcsicmp( String1, String2 );
  591. }
  592. INLINE
  593. LONG
  594. WSTRING::Strcmp(
  595. IN PCWSTRING String,
  596. IN CHNUM LeftPosition
  597. ) CONST
  598. /*++
  599. Routine Description:
  600. This routine compares two strings. It starts comparing the
  601. current string at the given position.
  602. Arguments:
  603. String - Supplies the string to compare to.
  604. LeftPosition - Supplies the starting position to start comparison
  605. on the current string.
  606. Return Value:
  607. < 0 - This string is less than the given string.
  608. 0 - This string is equal to the given string.
  609. > 0 - This string is greater than the given string.
  610. --*/
  611. {
  612. return wcscmp(_s + LeftPosition, String->_s);
  613. }
  614. INLINE
  615. LONG
  616. WSTRING::Stricmp(
  617. IN PCWSTRING String
  618. ) CONST
  619. /*++
  620. Routine Description:
  621. This routine compares two strings insensitive of case.
  622. Arguments:
  623. String - Supplies the string to compare to.
  624. Return Value:
  625. < 0 - This string is less than the given string.
  626. 0 - This string is equal to the given string.
  627. > 0 - This string is greater than the given string.
  628. --*/
  629. {
  630. return _wcsicmp(_s, String->_s);
  631. }
  632. INLINE
  633. LONG
  634. WSTRING::Stricmp(
  635. IN PCWSTRING String,
  636. IN CHNUM LeftPosition
  637. ) CONST
  638. /*++
  639. Routine Description:
  640. This routine compares two strings insensitive of case.
  641. Arguments:
  642. String - Supplies the string to compare to.
  643. LeftPosition - Supplies the position in this string to start
  644. comparison.
  645. Return Value:
  646. < 0 - This string is less than the given string.
  647. 0 - This string is equal to the given string.
  648. > 0 - This string is greater than the given string.
  649. --*/
  650. {
  651. return _wcsicmp(_s + LeftPosition, String->_s);
  652. }
  653. INLINE
  654. PWSTRING
  655. WSTRING::Strupr(
  656. )
  657. /*++
  658. Routine Description:
  659. This routine uppercases this string.
  660. Arguments:
  661. None.
  662. Return Value:
  663. None.
  664. --*/
  665. {
  666. #if !defined( _EFICHECK_ )
  667. // BUGBUG there's no upcase function in the EFI library
  668. // hopefully this won't have terrible side effects
  669. _wcsupr(_s);
  670. #endif
  671. return this;
  672. }
  673. INLINE
  674. PWSTRING
  675. WSTRING::Strlwr(
  676. )
  677. /*++
  678. Routine Description:
  679. This routine lowercases this string.
  680. Arguments:
  681. None.
  682. Return Value:
  683. None.
  684. --*/
  685. {
  686. #if !defined( _EFICHECK_ )
  687. // BUGBUG no lowercase function in EFI library
  688. // hopefully this won't result in bad side effects
  689. _wcslwr(_s);
  690. #endif
  691. return this;
  692. }
  693. INLINE
  694. CHNUM
  695. WSTRING::Strchr(
  696. IN WCHAR Char,
  697. IN CHNUM StartPosition
  698. ) CONST
  699. /*++
  700. Routine Description:
  701. This routine returns the position of the first occurance of
  702. the given character.
  703. Arguments:
  704. Char - Supplies the character to find.
  705. Return Value:
  706. The position of the given character or INVALID_CHNUM.
  707. --*/
  708. {
  709. #if !defined( _EFICHECK_ )
  710. PWSTR p;
  711. DebugAssert(StartPosition <= _l);
  712. p = wcschr(_s + StartPosition, Char);
  713. return p ? (CHNUM)(p - _s) : INVALID_CHNUM;
  714. #else
  715. UINT32 charnum;
  716. for( charnum = 0; charnum <= _l; charnum++ ) {
  717. if( _s[charnum] == Char ) {
  718. break;
  719. }
  720. }
  721. if ( charnum >= _l ) {
  722. return INVALID_CHNUM;
  723. } else {
  724. return charnum;
  725. }
  726. #endif
  727. }
  728. INLINE
  729. CHNUM
  730. WSTRING::Strrchr(
  731. IN WCHAR Char,
  732. IN CHNUM StartPosition
  733. ) CONST
  734. /*++
  735. Routine Description:
  736. This routine returns the position of the last occurance of
  737. the given character.
  738. Arguments:
  739. Char - Supplies the character to find.
  740. Return Value:
  741. The position of the given character or INVALID_CHNUM.
  742. --*/
  743. {
  744. #if !defined( _EFICHECK_)
  745. PWSTR p;
  746. p = wcsrchr(_s + StartPosition, Char);
  747. return p ? (CHNUM)(p - _s) : INVALID_CHNUM;
  748. #else
  749. UINT32 charnum;
  750. for( charnum = _l; charnum >= StartPosition; charnum-- ) {
  751. if( _s[charnum] == Char ) {
  752. break;
  753. }
  754. }
  755. if( (CHNUM)charnum < StartPosition ) {
  756. return INVALID_CHNUM;
  757. } else {
  758. return charnum;
  759. }
  760. #endif
  761. }
  762. INLINE
  763. CHNUM
  764. WSTRING::Strstr(
  765. IN PCWSTRING String
  766. ) CONST
  767. /*++
  768. Routine Description:
  769. This routine finds the given string withing this string.
  770. Arguments:
  771. String - Supplies the string to find.
  772. Return Value:
  773. The position of the given string in this string or INVALID_CHNUM.
  774. --*/
  775. {
  776. #if !defined( _EFICHECK_ )
  777. PWSTR p;
  778. p = wcsstr(_s, String->_s);
  779. return p ? (CHNUM)(p - _s) : INVALID_CHNUM;
  780. #else
  781. UINT32 pos;
  782. UINT32 pos2;
  783. UINT32 pos3;
  784. UINT32 len;
  785. UINT32 match = FALSE;
  786. len = (UINT32)StrLen(String->_s);
  787. // if the string is short than the substr, no match
  788. if (len > _l ) {
  789. return (CHNUM)INVALID_CHNUM;
  790. }
  791. // iterate from start to start - len
  792. for (pos=0; pos < _l - len; pos++ ) {
  793. // iterate from pos to pos+len
  794. match = TRUE;
  795. for(pos2 = pos,pos3=0; pos2 < pos+len; pos2++,pos3++ ) {
  796. // if we ever get a mismatch, break and advance the start of the compare.
  797. if(_s[pos2] != String->_s[pos3]) {
  798. match = FALSE;
  799. break;
  800. }
  801. }
  802. if( match == TRUE ) {
  803. return (CHNUM)pos;
  804. }
  805. }
  806. return (CHNUM)INVALID_CHNUM;
  807. #endif
  808. }
  809. INLINE
  810. CHNUM
  811. WSTRING::Strspn(
  812. IN PCWSTRING String,
  813. IN CHNUM StartPosition
  814. ) CONST
  815. /*++
  816. Routine Description:
  817. This routine returns the position of the first character in this
  818. string that does not belong to the set of characters in the given
  819. string.
  820. Arguments:
  821. String - Supplies the list of characters to search for.
  822. Return Value:
  823. The position of the first character found that does not belong
  824. to the given string.
  825. --*/
  826. {
  827. #if !defined( _EFICHECK_ )
  828. CHNUM r;
  829. DebugAssert(StartPosition <= _l);
  830. r = wcsspn(_s + StartPosition, String->_s) + StartPosition;
  831. return r < _l ? r : INVALID_CHNUM;
  832. #else
  833. UINT32 match = FALSE;
  834. UINT32 pos;
  835. UINT32 pos2;
  836. UINT32 length = (UINT32)StrLen(String->_s);
  837. if (StartPosition > _l ) {
  838. return INVALID_CHNUM;
  839. }
  840. for( pos = StartPosition; pos < _l; pos++ ) {
  841. for( pos2 = 0; pos2 < length; pos2++) {
  842. if( String->_s[pos2] == _s[pos] ) {
  843. match = TRUE;
  844. }
  845. }
  846. if (match == FALSE) {
  847. break;
  848. }
  849. }
  850. if (match = FALSE) {
  851. return pos;
  852. } else {
  853. return INVALID_CHNUM;
  854. }
  855. #endif
  856. }
  857. INLINE
  858. CHNUM
  859. WSTRING::Strcspn(
  860. IN PCWSTRING String,
  861. IN CHNUM StartPosition
  862. ) CONST
  863. /*++
  864. Routine Description:
  865. This routine returns the position of the first character in this
  866. string that belongs to the set of characters in the given
  867. string.
  868. Arguments:
  869. String - Supplies the list of characters to search for.
  870. Return Value:
  871. Returns the position of the first character in this string
  872. belonging to the given string or INVALID_CHNUM.
  873. --*/
  874. {
  875. #if !defined( _EFICHECK_ )
  876. CHNUM r;
  877. DebugAssert(StartPosition <= _l);
  878. r = wcscspn(_s + StartPosition, String->_s) + StartPosition;
  879. return r < _l ? r : INVALID_CHNUM;
  880. #else
  881. UINT32 nomatch = FALSE;
  882. UINT32 pos;
  883. UINT32 pos2;
  884. UINT32 length = (UINT32)StrLen(String->_s);
  885. if (StartPosition > _l ) {
  886. return INVALID_CHNUM;
  887. }
  888. for( pos = StartPosition; pos < _l; pos++ ) {
  889. for( pos2 = 0; pos2 < length; pos2++) {
  890. if( String->_s[pos2] != _s[pos] ) {
  891. nomatch = TRUE;
  892. }
  893. }
  894. if (nomatch == FALSE) {
  895. break;
  896. }
  897. }
  898. if (nomatch = FALSE) {
  899. return pos;
  900. } else {
  901. return INVALID_CHNUM;
  902. }
  903. #endif
  904. }
  905. INLINE
  906. BOOLEAN
  907. WSTRING::operator==(
  908. IN RCWSTRING String
  909. ) CONST
  910. {
  911. return Stricmp(&String) == 0;
  912. }
  913. INLINE
  914. BOOLEAN
  915. WSTRING::operator!=(
  916. IN RCWSTRING String
  917. ) CONST
  918. {
  919. return Stricmp(&String) != 0;
  920. }
  921. INLINE
  922. BOOLEAN
  923. WSTRING::operator<(
  924. IN RCWSTRING String
  925. ) CONST
  926. {
  927. return Stricmp(&String) < 0;
  928. }
  929. INLINE
  930. BOOLEAN
  931. WSTRING::operator>(
  932. IN RCWSTRING String
  933. ) CONST
  934. {
  935. return Stricmp(&String) > 0;
  936. }
  937. INLINE
  938. BOOLEAN
  939. WSTRING::operator<=(
  940. IN RCWSTRING String
  941. ) CONST
  942. {
  943. return Stricmp(&String) <= 0;
  944. }
  945. INLINE
  946. BOOLEAN
  947. WSTRING::operator>=(
  948. IN RCWSTRING String
  949. ) CONST
  950. {
  951. return Stricmp(&String) >= 0;
  952. }
  953. INLINE
  954. CHNUM
  955. WSTRING::Truncate(
  956. IN CHNUM Position
  957. )
  958. {
  959. DebugAssert(Position <= _l);
  960. Resize(Position);
  961. return _l;
  962. }
  963. DECLARE_CLASS( FSTRING );
  964. class ULIB_EXPORT FSTRING : public WSTRING {
  965. public:
  966. DECLARE_CONSTRUCTOR( FSTRING );
  967. NONVIRTUAL
  968. PWSTRING
  969. Initialize(
  970. IN OUT PWSTR InitialString,
  971. IN CHNUM BufferLength DEFAULT TO_END
  972. );
  973. VIRTUAL
  974. BOOLEAN
  975. Resize(
  976. IN CHNUM NewStringLength
  977. );
  978. VIRTUAL
  979. BOOLEAN
  980. NewBuf(
  981. IN CHNUM NewStringLength
  982. );
  983. private:
  984. CHNUM _buffer_length;
  985. };
  986. INLINE
  987. PWSTRING
  988. FSTRING::Initialize(
  989. IN OUT PWSTR InitialString,
  990. IN CHNUM BufferLength
  991. )
  992. /*++
  993. Routine Description:
  994. This routine initializes this class with a null-terminated
  995. unicode string. This routine does not make a copy of the string
  996. but uses it as is.
  997. Arguments:
  998. NullTerminatedString - Supplies a null-terminated unicode string.
  999. BufferLength - Supplies the buffer length.
  1000. Return Value:
  1001. A pointer to this class.
  1002. --*/
  1003. {
  1004. PutString(InitialString);
  1005. _buffer_length = ((BufferLength == TO_END) ?
  1006. (QueryChCount() + 1) : BufferLength);
  1007. return this;
  1008. }
  1009. DECLARE_CLASS( DSTRING );
  1010. class ULIB_EXPORT DSTRING : public WSTRING {
  1011. public:
  1012. DECLARE_CONSTRUCTOR( DSTRING );
  1013. VIRTUAL
  1014. ~DSTRING(
  1015. );
  1016. VIRTUAL
  1017. BOOLEAN
  1018. Resize(
  1019. IN CHNUM NewStringLength
  1020. );
  1021. VIRTUAL
  1022. BOOLEAN
  1023. NewBuf(
  1024. IN CHNUM NewStringLength
  1025. );
  1026. private:
  1027. VOID
  1028. Construct(
  1029. );
  1030. PWSTR _buf; // String buffer.
  1031. CHNUM _length; // Number of characters in buffer.
  1032. };
  1033. #endif // _WSTRING_DEFN_