PageRenderTime 55ms CodeModel.GetById 30ms RepoModel.GetById 0ms app.codeStats 0ms

/Zend/Search/Lucene/Storage/File/Memory.php

https://bitbucket.org/freddixx/e-business-vcrm-plugin
PHP | 555 lines | 244 code | 75 blank | 236 comment | 40 complexity | b565e88296f4c12604a0abb3f3534f28 MD5 | raw file
  1. <?php
  2. /**
  3. * Zend Framework
  4. *
  5. * LICENSE
  6. *
  7. * This source file is subject to the new BSD license that is bundled
  8. * with this package in the file LICENSE.txt.
  9. * It is also available through the world-wide-web at this URL:
  10. * http://framework.zend.com/license/new-bsd
  11. * If you did not receive a copy of the license and are unable to
  12. * obtain it through the world-wide-web, please send an email
  13. * to license@zend.com so we can send you a copy immediately.
  14. *
  15. * @category Zend
  16. * @package Zend_Search_Lucene
  17. * @subpackage Storage
  18. * @copyright Copyright (c) 2005-2008 Zend Technologies USA Inc. (http://www.zend.com)
  19. * @license http://framework.zend.com/license/new-bsd New BSD License
  20. */
  21. /** Zend_Search_Lucene_Storage_File */
  22. require_once 'Zend/Search/Lucene/Storage/File.php';
  23. /** Zend_Search_Lucene_Exception */
  24. require_once 'Zend/Search/Lucene/Exception.php';
  25. /**
  26. * @category Zend
  27. * @package Zend_Search_Lucene
  28. * @subpackage Storage
  29. * @copyright Copyright (c) 2005-2008 Zend Technologies USA Inc. (http://www.zend.com)
  30. * @license http://framework.zend.com/license/new-bsd New BSD License
  31. */
  32. class Zend_Search_Lucene_Storage_File_Memory extends Zend_Search_Lucene_Storage_File
  33. {
  34. /**
  35. * FileData
  36. *
  37. * @var string
  38. */
  39. private $_data;
  40. /**
  41. * File Position
  42. *
  43. * @var integer
  44. */
  45. private $_position = 0;
  46. /**
  47. * Object constractor
  48. *
  49. * @param string $data
  50. */
  51. public function __construct($data)
  52. {
  53. $this->_data = $data;
  54. }
  55. /**
  56. * Reads $length number of bytes at the current position in the
  57. * file and advances the file pointer.
  58. *
  59. * @param integer $length
  60. * @return string
  61. */
  62. protected function _fread($length = 1)
  63. {
  64. $returnValue = substr($this->_data, $this->_position, $length);
  65. $this->_position += $length;
  66. return $returnValue;
  67. }
  68. /**
  69. * Sets the file position indicator and advances the file pointer.
  70. * The new position, measured in bytes from the beginning of the file,
  71. * is obtained by adding offset to the position specified by whence,
  72. * whose values are defined as follows:
  73. * SEEK_SET - Set position equal to offset bytes.
  74. * SEEK_CUR - Set position to current location plus offset.
  75. * SEEK_END - Set position to end-of-file plus offset. (To move to
  76. * a position before the end-of-file, you need to pass a negative value
  77. * in offset.)
  78. * Upon success, returns 0; otherwise, returns -1
  79. *
  80. * @param integer $offset
  81. * @param integer $whence
  82. * @return integer
  83. */
  84. public function seek($offset, $whence=SEEK_SET)
  85. {
  86. switch ($whence) {
  87. case SEEK_SET:
  88. $this->_position = $offset;
  89. break;
  90. case SEEK_CUR:
  91. $this->_position += $offset;
  92. break;
  93. case SEEK_END:
  94. $this->_position = strlen($this->_data);
  95. $this->_position += $offset;
  96. break;
  97. default:
  98. break;
  99. }
  100. }
  101. /**
  102. * Get file position.
  103. *
  104. * @return integer
  105. */
  106. public function tell()
  107. {
  108. return $this->_position;
  109. }
  110. /**
  111. * Flush output.
  112. *
  113. * Returns true on success or false on failure.
  114. *
  115. * @return boolean
  116. */
  117. public function flush()
  118. {
  119. // Do nothing
  120. return true;
  121. }
  122. /**
  123. * Writes $length number of bytes (all, if $length===null) to the end
  124. * of the file.
  125. *
  126. * @param string $data
  127. * @param integer $length
  128. */
  129. protected function _fwrite($data, $length=null)
  130. {
  131. // We do not need to check if file position points to the end of "file".
  132. // Only append operation is supported now
  133. if ($length !== null) {
  134. $this->_data .= substr($data, 0, $length);
  135. } else {
  136. $this->_data .= $data;
  137. }
  138. $this->_position = strlen($this->_data);
  139. }
  140. /**
  141. * Lock file
  142. *
  143. * Lock type may be a LOCK_SH (shared lock) or a LOCK_EX (exclusive lock)
  144. *
  145. * @param integer $lockType
  146. * @return boolean
  147. */
  148. public function lock($lockType, $nonBlockinLock = false)
  149. {
  150. // Memory files can't be shared
  151. // do nothing
  152. return true;
  153. }
  154. /**
  155. * Unlock file
  156. */
  157. public function unlock()
  158. {
  159. // Memory files can't be shared
  160. // do nothing
  161. }
  162. /**
  163. * Reads a byte from the current position in the file
  164. * and advances the file pointer.
  165. *
  166. * @return integer
  167. */
  168. public function readByte()
  169. {
  170. return ord($this->_data[$this->_position++]);
  171. }
  172. /**
  173. * Writes a byte to the end of the file.
  174. *
  175. * @param integer $byte
  176. */
  177. public function writeByte($byte)
  178. {
  179. // We do not need to check if file position points to the end of "file".
  180. // Only append operation is supported now
  181. $this->_data .= chr($byte);
  182. $this->_position = strlen($this->_data);
  183. return 1;
  184. }
  185. /**
  186. * Read num bytes from the current position in the file
  187. * and advances the file pointer.
  188. *
  189. * @param integer $num
  190. * @return string
  191. */
  192. public function readBytes($num)
  193. {
  194. $returnValue = substr($this->_data, $this->_position, $num);
  195. $this->_position += $num;
  196. return $returnValue;
  197. }
  198. /**
  199. * Writes num bytes of data (all, if $num===null) to the end
  200. * of the string.
  201. *
  202. * @param string $data
  203. * @param integer $num
  204. */
  205. public function writeBytes($data, $num=null)
  206. {
  207. // We do not need to check if file position points to the end of "file".
  208. // Only append operation is supported now
  209. if ($num !== null) {
  210. $this->_data .= substr($data, 0, $num);
  211. } else {
  212. $this->_data .= $data;
  213. }
  214. $this->_position = strlen($this->_data);
  215. }
  216. /**
  217. * Reads an integer from the current position in the file
  218. * and advances the file pointer.
  219. *
  220. * @return integer
  221. */
  222. public function readInt()
  223. {
  224. $str = substr($this->_data, $this->_position, 4);
  225. $this->_position += 4;
  226. return ord($str[0]) << 24 |
  227. ord($str[1]) << 16 |
  228. ord($str[2]) << 8 |
  229. ord($str[3]);
  230. }
  231. /**
  232. * Writes an integer to the end of file.
  233. *
  234. * @param integer $value
  235. */
  236. public function writeInt($value)
  237. {
  238. // We do not need to check if file position points to the end of "file".
  239. // Only append operation is supported now
  240. settype($value, 'integer');
  241. $this->_data .= chr($value>>24 & 0xFF) .
  242. chr($value>>16 & 0xFF) .
  243. chr($value>>8 & 0xFF) .
  244. chr($value & 0xFF);
  245. $this->_position = strlen($this->_data);
  246. }
  247. /**
  248. * Returns a long integer from the current position in the file
  249. * and advances the file pointer.
  250. *
  251. * @return integer
  252. * @throws Zend_Search_Lucene_Exception
  253. */
  254. public function readLong()
  255. {
  256. $str = substr($this->_data, $this->_position, 8);
  257. $this->_position += 8;
  258. /**
  259. * Check, that we work in 64-bit mode.
  260. * fseek() uses long for offset. Thus, largest index segment file size in 32bit mode is 2Gb
  261. */
  262. if (PHP_INT_SIZE > 4) {
  263. return ord($str[0]) << 56 |
  264. ord($str[1]) << 48 |
  265. ord($str[2]) << 40 |
  266. ord($str[3]) << 32 |
  267. ord($str[4]) << 24 |
  268. ord($str[5]) << 16 |
  269. ord($str[6]) << 8 |
  270. ord($str[7]);
  271. } else {
  272. if ((ord($str[0]) != 0) ||
  273. (ord($str[1]) != 0) ||
  274. (ord($str[2]) != 0) ||
  275. (ord($str[3]) != 0) ||
  276. ((ord($str[0]) & 0x80) != 0)) {
  277. throw new Zend_Search_Lucene_Exception('Largest supported segment size (for 32-bit mode) is 2Gb');
  278. }
  279. return ord($str[4]) << 24 |
  280. ord($str[5]) << 16 |
  281. ord($str[6]) << 8 |
  282. ord($str[7]);
  283. }
  284. }
  285. /**
  286. * Writes long integer to the end of file
  287. *
  288. * @param integer $value
  289. * @throws Zend_Search_Lucene_Exception
  290. */
  291. public function writeLong($value)
  292. {
  293. // We do not need to check if file position points to the end of "file".
  294. // Only append operation is supported now
  295. /**
  296. * Check, that we work in 64-bit mode.
  297. * fseek() and ftell() use long for offset. Thus, largest index segment file size in 32bit mode is 2Gb
  298. */
  299. if (PHP_INT_SIZE > 4) {
  300. settype($value, 'integer');
  301. $this->_data .= chr($value>>56 & 0xFF) .
  302. chr($value>>48 & 0xFF) .
  303. chr($value>>40 & 0xFF) .
  304. chr($value>>32 & 0xFF) .
  305. chr($value>>24 & 0xFF) .
  306. chr($value>>16 & 0xFF) .
  307. chr($value>>8 & 0xFF) .
  308. chr($value & 0xFF);
  309. } else {
  310. if ($value > 0x7FFFFFFF) {
  311. throw new Zend_Search_Lucene_Exception('Largest supported segment size (for 32-bit mode) is 2Gb');
  312. }
  313. $this->_data .= chr(0) . chr(0) . chr(0) . chr(0) .
  314. chr($value>>24 & 0xFF) .
  315. chr($value>>16 & 0xFF) .
  316. chr($value>>8 & 0xFF) .
  317. chr($value & 0xFF);
  318. }
  319. $this->_position = strlen($this->_data);
  320. }
  321. /**
  322. * Returns a variable-length integer from the current
  323. * position in the file and advances the file pointer.
  324. *
  325. * @return integer
  326. */
  327. public function readVInt()
  328. {
  329. $nextByte = ord($this->_data[$this->_position++]);
  330. $val = $nextByte & 0x7F;
  331. for ($shift=7; ($nextByte & 0x80) != 0; $shift += 7) {
  332. $nextByte = ord($this->_data[$this->_position++]);
  333. $val |= ($nextByte & 0x7F) << $shift;
  334. }
  335. return $val;
  336. }
  337. /**
  338. * Writes a variable-length integer to the end of file.
  339. *
  340. * @param integer $value
  341. */
  342. public function writeVInt($value)
  343. {
  344. // We do not need to check if file position points to the end of "file".
  345. // Only append operation is supported now
  346. settype($value, 'integer');
  347. while ($value > 0x7F) {
  348. $this->_data .= chr( ($value & 0x7F)|0x80 );
  349. $value >>= 7;
  350. }
  351. $this->_data .= chr($value);
  352. $this->_position = strlen($this->_data);
  353. }
  354. /**
  355. * Reads a string from the current position in the file
  356. * and advances the file pointer.
  357. *
  358. * @return string
  359. */
  360. public function readString()
  361. {
  362. $strlen = $this->readVInt();
  363. if ($strlen == 0) {
  364. return '';
  365. } else {
  366. /**
  367. * This implementation supports only Basic Multilingual Plane
  368. * (BMP) characters (from 0x0000 to 0xFFFF) and doesn't support
  369. * "supplementary characters" (characters whose code points are
  370. * greater than 0xFFFF)
  371. * Java 2 represents these characters as a pair of char (16-bit)
  372. * values, the first from the high-surrogates range (0xD800-0xDBFF),
  373. * the second from the low-surrogates range (0xDC00-0xDFFF). Then
  374. * they are encoded as usual UTF-8 characters in six bytes.
  375. * Standard UTF-8 representation uses four bytes for supplementary
  376. * characters.
  377. */
  378. $str_val = substr($this->_data, $this->_position, $strlen);
  379. $this->_position += $strlen;
  380. for ($count = 0; $count < $strlen; $count++ ) {
  381. if (( ord($str_val[$count]) & 0xC0 ) == 0xC0) {
  382. $addBytes = 1;
  383. if (ord($str_val[$count]) & 0x20 ) {
  384. $addBytes++;
  385. // Never used. Java2 doesn't encode strings in four bytes
  386. if (ord($str_val[$count]) & 0x10 ) {
  387. $addBytes++;
  388. }
  389. }
  390. $str_val .= substr($this->_data, $this->_position, $addBytes);
  391. $this->_position += $addBytes;
  392. $strlen += $addBytes;
  393. // Check for null character. Java2 encodes null character
  394. // in two bytes.
  395. if (ord($str_val[$count]) == 0xC0 &&
  396. ord($str_val[$count+1]) == 0x80 ) {
  397. $str_val[$count] = 0;
  398. $str_val = substr($str_val,0,$count+1)
  399. . substr($str_val,$count+2);
  400. }
  401. $count += $addBytes;
  402. }
  403. }
  404. return $str_val;
  405. }
  406. }
  407. /**
  408. * Writes a string to the end of file.
  409. *
  410. * @param string $str
  411. * @throws Zend_Search_Lucene_Exception
  412. */
  413. public function writeString($str)
  414. {
  415. /**
  416. * This implementation supports only Basic Multilingual Plane
  417. * (BMP) characters (from 0x0000 to 0xFFFF) and doesn't support
  418. * "supplementary characters" (characters whose code points are
  419. * greater than 0xFFFF)
  420. * Java 2 represents these characters as a pair of char (16-bit)
  421. * values, the first from the high-surrogates range (0xD800-0xDBFF),
  422. * the second from the low-surrogates range (0xDC00-0xDFFF). Then
  423. * they are encoded as usual UTF-8 characters in six bytes.
  424. * Standard UTF-8 representation uses four bytes for supplementary
  425. * characters.
  426. */
  427. // We do not need to check if file position points to the end of "file".
  428. // Only append operation is supported now
  429. // convert input to a string before iterating string characters
  430. settype($str, 'string');
  431. $chars = $strlen = strlen($str);
  432. $containNullChars = false;
  433. for ($count = 0; $count < $strlen; $count++ ) {
  434. /**
  435. * String is already in Java 2 representation.
  436. * We should only calculate actual string length and replace
  437. * \x00 by \xC0\x80
  438. */
  439. if ((ord($str[$count]) & 0xC0) == 0xC0) {
  440. $addBytes = 1;
  441. if (ord($str[$count]) & 0x20 ) {
  442. $addBytes++;
  443. // Never used. Java2 doesn't encode strings in four bytes
  444. // and we dont't support non-BMP characters
  445. if (ord($str[$count]) & 0x10 ) {
  446. $addBytes++;
  447. }
  448. }
  449. $chars -= $addBytes;
  450. if (ord($str[$count]) == 0 ) {
  451. $containNullChars = true;
  452. }
  453. $count += $addBytes;
  454. }
  455. }
  456. if ($chars < 0) {
  457. throw new Zend_Search_Lucene_Exception('Invalid UTF-8 string');
  458. }
  459. $this->writeVInt($chars);
  460. if ($containNullChars) {
  461. $this->_data .= str_replace($str, "\x00", "\xC0\x80");
  462. } else {
  463. $this->_data .= $str;
  464. }
  465. $this->_position = strlen($this->_data);
  466. }
  467. /**
  468. * Reads binary data from the current position in the file
  469. * and advances the file pointer.
  470. *
  471. * @return string
  472. */
  473. public function readBinary()
  474. {
  475. $length = $this->readVInt();
  476. $returnValue = substr($this->_data, $this->_position, $length);
  477. $this->_position += $length;
  478. return $returnValue;
  479. }
  480. }