murfy Posted December 10, 2013 Share Posted December 10, 2013 I created a class which should creates new binary file (called 4.ip) in the case that the file does not exist. Method reset() does the job. Then I try to add some numbers from Ip to the file. I try to use binary mode but It looks like it corrupts the file. First value 0E is written correctly. I have marked the BOM which was created in the reset method (idk if is this right when it should be binary file. To see the above, uncomment the die(); on line 413. Then to see the bellow, comment it back. When I try to write the second value (line 415), the file looks corrupted, and all the 0000 disappear. This is the source code: http://paste.ofcode.org/v8M4DwrH7hQzkJMEDjaRpt please see the lines 412-418. <?php include("scan_ips_class.php"); $scanIPs = new Scan_ips; ?> Please help because I really cannot find out solution, and I am lost. Trying to solve this few days. Quote Link to comment https://forums.phpfreaks.com/topic/284681-binary-fwrite-in-mode-rb/ Share on other sites More sharing options...
Barand Posted December 10, 2013 Share Posted December 10, 2013 Do not double post. Quote Link to comment https://forums.phpfreaks.com/topic/284681-binary-fwrite-in-mode-rb/#findComment-1461929 Share on other sites More sharing options...
murfy Posted December 10, 2013 Author Share Posted December 10, 2013 Do not double post. What? Quote Link to comment https://forums.phpfreaks.com/topic/284681-binary-fwrite-in-mode-rb/#findComment-1461931 Share on other sites More sharing options...
Barand Posted December 10, 2013 Share Posted December 10, 2013 You posted the identical question 22 minutes before posting this one Quote Link to comment https://forums.phpfreaks.com/topic/284681-binary-fwrite-in-mode-rb/#findComment-1461939 Share on other sites More sharing options...
murfy Posted December 10, 2013 Author Share Posted December 10, 2013 You posted the identical question 22 minutes before posting this one I don't know about this, how this happened. I edited the post only. Quote Link to comment https://forums.phpfreaks.com/topic/284681-binary-fwrite-in-mode-rb/#findComment-1461942 Share on other sites More sharing options...
murfy Posted December 10, 2013 Author Share Posted December 10, 2013 (edited) Yet I show you working version which is simplified. This uses no class: http://paste.ofcode.org/8ipwC6eWGPxZpHGK5DQFmg so you can see how it works. The written data do not corrupt the file. But why I cannot use the class to do that? Edited December 10, 2013 by murfy Quote Link to comment https://forums.phpfreaks.com/topic/284681-binary-fwrite-in-mode-rb/#findComment-1461947 Share on other sites More sharing options...
kicken Posted December 10, 2013 Share Posted December 10, 2013 Your code does not generate the BOM mark when I try it, and I see no reason why it should. I'd suspect you are somehow modifying the file after the fact, such as by opening it in an editor that automatically adds the BOM. on a side note, your loop in the reset method could be simplified into $t = str_repeat(chr(0), $this->bufferSize); Quote Link to comment https://forums.phpfreaks.com/topic/284681-binary-fwrite-in-mode-rb/#findComment-1461972 Share on other sites More sharing options...
murfy Posted December 10, 2013 Author Share Posted December 10, 2013 Your code does not generate the BOM mark when I try it, and I see no reason why it should. I'd suspect you are somehow modifying the file after the fact, such as by opening it in an editor that automatically adds the BOM. on a side note, your loop in the reset method could be simplified into $t = str_repeat(chr(0), $this->bufferSize); Thanks for this piece of code, can be useful. But did you see the file to be corrupted or not? Can you find the reason why it corrupts? In recent post I have added the second version, which is working, so I would like to know if you noticed same problem like me. Quote Link to comment https://forums.phpfreaks.com/topic/284681-binary-fwrite-in-mode-rb/#findComment-1461996 Share on other sites More sharing options...
kicken Posted December 10, 2013 Share Posted December 10, 2013 Are you talking about the BOM mark being the corruption, or the fact that all your null characters disappear? I may have mis-understood your initial post. fwiw, the comments over on devshed about this being a fairly dumb thing to do just to store a list if IPs are accurate. With your fairly limited list of IP's you could just store them one per line or similar and be done with it without having to futz around with all this binary reading/writing/seeking etc. Your code would be drastically simplified and perform just as well. Quote Link to comment https://forums.phpfreaks.com/topic/284681-binary-fwrite-in-mode-rb/#findComment-1462007 Share on other sites More sharing options...
murfy Posted December 11, 2013 Author Share Posted December 11, 2013 1) I don't know if the BOM mark is a corruption when it is there in binary file. I have no idea how it was generated. 2) When the BOM mark disapears it could be taken as a corruption of BOM mark 3) Yes, the 0000 data disapear till the end of file, so this is corruption too I wanted to do it binary to gain a speedy approach. The first write to this file should have about 120-140 IPs and then just adding few IPs per minute would be nice. I know I could simply add it to txt file, but then when I would want to make sure that the IP is not in the list I would need to search whole file if it contains the IP. Why do you think that simple file solution would be better performance? This is ideal I think, I just jump to one segment to check if some IP is there. In the moment I have working class but it writes only 3 bytes of the first IP, and the next IP corrupts the file, so I want to find the cause today. Hopefully I will solve it today. Do you think that file seeking is slower because it is on hard drive than search in heap which is in RAM? Quote Link to comment https://forums.phpfreaks.com/topic/284681-binary-fwrite-in-mode-rb/#findComment-1462047 Share on other sites More sharing options...
murfy Posted December 11, 2013 Author Share Posted December 11, 2013 Also if the fseek makes it slow I can change it to read all three segments of 250 bytes and then loop it in RAM memory. Quote Link to comment https://forums.phpfreaks.com/topic/284681-binary-fwrite-in-mode-rb/#findComment-1462048 Share on other sites More sharing options...
murfy Posted December 11, 2013 Author Share Posted December 11, 2013 (edited) Also, can you help with this? I found that when I write a byte it uses two bytes instead one: so the number 64 should be correctly in the blue circle. There should be 7864 5E3C because here I have inserted 4 numbers: 120, 100 and 94, 60. So the result is like it uses Unicode because ot the unicode BOM which is on the begin of file. How should I create the file without the BOM, to have standard binary file behaviour? This is strange. I created the file with xb option and then added the string like this: fwrite($fh,$t); Yet I did a check of length die(strlen($t).""); // 750*254=190500 is OK. This looks like the buffer size is correct but still, why it is written in wrong way? Edited December 11, 2013 by murfy Quote Link to comment https://forums.phpfreaks.com/topic/284681-binary-fwrite-in-mode-rb/#findComment-1462060 Share on other sites More sharing options...
murfy Posted December 11, 2013 Author Share Posted December 11, 2013 (edited) Solved: This is error of the viewer. Notepad++ Hexa editor does not show the BOM and shows correct positions of bytes. Edited December 11, 2013 by murfy Quote Link to comment https://forums.phpfreaks.com/topic/284681-binary-fwrite-in-mode-rb/#findComment-1462079 Share on other sites More sharing options...
kicken Posted December 11, 2013 Share Posted December 11, 2013 Why do you think that simple file solution would be better performance?I didn't say it'd have better performance, I said it'd probably be just as good (though it may be better). In any event the performance difference between your messy binary system and a plain text system is probably so minor that it's not even worth mentioning. A plain text system would be far easier to code however and much more readable. You could make things even simpler by letting PHP do a lot of the work and just used a stored array and include(). I've done this for a number of small lists or configuration files: function checkIP($ip){ $ipList = include('ips.php'); return in_array($ip, $ipList); } function addIP($ip){ if (checkIP($ip)) return; $ipList = include('ips.php'); $ipList[] = $ip; file_put_contents('ips.php', '<?php return '.var_export($ipList, true).';'); } See how much simpler that code is? Quote Link to comment https://forums.phpfreaks.com/topic/284681-binary-fwrite-in-mode-rb/#findComment-1462083 Share on other sites More sharing options...
murfy Posted December 12, 2013 Author Share Posted December 12, 2013 (edited) Of sure your solution is simple and I also use it for different things. But it's true that I did not do any real site for real traffic using RS. I would like to do one site with RS and use there the IP container. But because IP list is demanded to be offten readed and offen searched for exact item (comparison two items) so I thought it could be good idea. It is not problem to me to make the class. When you realize that sites which uses RS contains many classes, so one more class is just a simple thing. Because to me it looks much more complicated to think up and realize class for mysql or for management of the web content than to do this simple class. I know it can look complicated because it has methods, but this is exactly what I see as advantage. Classes benefit is that they bring more readability to the code... Of sore, reading a simple file is very short code, but also you must read and compare much more data... I am not sure If I mentioned the concept of the container. I have reserved 250 bytes for three numbers of IP, which is 750 per a "row". So when you have IP 124.1.2.3 then I find the row 124 which is on position 750*124 - 1. The row of 750 is divided to 250 because 250 for second number, 250 for third number and 250 for fourth number. Now when I search for IP I have two approches and I must decide which one is better? A) either read first byte of the row (1st byte of the 1st segment:i) and then compare it with the second number of IP. If this is equal, so I seek for the second segment first byte (i+500) and compare with third number. If it is equal, so I do the same for the fourth number (i=750). I can repeat it as many times as needed. Of sure, that if there is not equality, than is will not be returned false (existing item). This means, that it will skip most of the bytes. I think there should be about 3-10 IPS in every row, so I read about cca 5-30 bytes only. But the problem here can be the fseek, which mean often to change the position to read. B) another solution would be to read all 3 segments to variables $a=fread($fh,250);$b=fread($fh,250);$c=fread($fh,250); and then when they are in RAM memory do quick comparison with for loop. This would also read about 5-30 bytes, but the difference is that it would read whole 750 bytes and fseek would be called only 1x. So what approach could be better? What do you think? Edited December 12, 2013 by murfy Quote Link to comment https://forums.phpfreaks.com/topic/284681-binary-fwrite-in-mode-rb/#findComment-1462189 Share on other sites More sharing options...
Recommended Posts
Join the conversation
You can post now and register later. If you have an account, sign in now to post with your account.