how to scan a hex file and then search for the required byte and display

in the file A5 5A should occur after 17 bytes so how to search it and conform it occurs only after 17 bytes then display the 5th and 6th byte starting from A5 and 5A. Could you please help me? , I have read your answer similar to it but couldnot manipulate the program accordingly.

4 Comments

Can you show your data? so that answer could be given clearly?
Is the HEX file actually a text file formatted as 2 characters, space, 2 characters, space, and so on, or is it a binary file?
The file is as follows.. can you please help me??
ACKNOWLEDGEMENT:
Thanks for your suggestion to: @sixwwwwww

Sign in to comment.

 Accepted Answer

Dear Prabhav, you can do it as follows:
% Read file in the form of string
ID = fopen('filename.txt');
A = textscan(ID, '%s');
fclose(ID);
% Your array
A = A{:};
% Find the locations of bytes 'A5' within array
indA5 = find(ismember(A, 'A5'));
% Find the locations of bytes '5A' within array
ind5A = find(ismember(A, '5A'));
% Find whether all 'A5' and '5A' located consecutively
loc = all(ind5A - indA5 == 1);
% Find the difference in locations of two consectuve occurances of 'A5' and
% if the difference is 17 then stores 1 in variable 'difference' otherwise
% store '0'
difference = indA5(2:numel(indA5)) - indA5(1:numel(indA5) - 1) == 17;
I hope it is helpful. Good luck!

22 Comments

Thankyou so much, I really Appreciate it and it is really helpful.
while running the program ind5A is 125*1 and ind5A is 124*1 double so
??? Error using ==> minus Matrix dimensions must agree.
Error in ==> edited at 18 loc = all(ind5A - indA5 == 1);
can it be solved without manually deleting the extra 5A from the file?
you can do it as follows:
if numel(indA5) > numel(ind5A) && indA5(end) < numel(A)
for i = 1:numel(indA5)
loc(i) = strcmp(A{indA5(i) + 1}, '5A');
end
elseif numel(indA5) < numel(ind5A) && ind5A(end) < numel(A)
for i = 1:numel(ind5A)
loc(i) = strcmp(A{ind5A(i) - 1}, 'A5');
end
else
loc = ind5A - indA5 == 1;
end
wow!!!! it worked... Thank you so much.. You're my legend...
Is it possible to combine the 3rd and 4th term after each A55A??
Yes you can do it as follows:
for i = 1:numel(loc)
if i ~= numel(loc) && loc(i) == 1 && difference(i) == 1
fprintf('3rd and 4th terms after A5 and 5A are: %s and %s\n', A{indA5(i) + 4}, A{indA5(i) + 5})
else
fprintf('3rd and 4th terms after A5 and 5A are: %s and %s\n', A{indA5(i) + 4}, A{indA5(i) + 5})
end
end
sorry i meant to say the 3rd and 4th term combined as a decimal equivalent,
however, the output is after adding the last line of code.
3rd and 4th terms after A5 and 5A are: 00 and 00
where am I supposed to place the last for loop? i suppose i misplaced it.. Thankyou...
Here is the complete code:
% Read file in the form of string
ID = fopen('filename.txt');
A = textscan(ID, '%s');
fclose(ID);
% Your array
A = A{:};
% Find the locations of bytes 'A5' within array
indA5 = find(ismember(A, 'A5'));
% Find the locations of bytes '5A' within array
ind5A = find(ismember(A, '5A'));
% Find whether all 'A5' and '5A' located consecutively
if numel(indA5) > numel(ind5A) && indA5(end) < numel(A)
for i = 1:numel(indA5)
loc(i) = strcmp(A{indA5(i) + 1}, '5A');
end
elseif numel(indA5) < numel(ind5A) && ind5A(end) < numel(A)
for i = 1:numel(ind5A)
loc(i) = strcmp(A{ind5A(i) - 1}, 'A5');
end
else
loc = ind5A - indA5 == 1;
end
% Find the difference in locations of two consectuve occurances of 'A5' and
% if the difference is 17 then stores 1 in variable 'difference' otherwise
% store '0'
difference = indA5(2:numel(indA5)) - indA5(1:numel(indA5) - 1) == 17;
for i = 1:numel(loc)
if i ~= numel(loc) && loc(i) == 1 && difference(i) == 1
fprintf('The decimal equivalent of 3rd + 4th terms after A5 and 5A is: %d\n', hex2dec(A{indA5(i) + 4}) + hex2dec(A{indA5(i) + 5}))
elseif loc(i) == 1
fprintf('The decimal equivalent of 3rd + 4th terms after A5 and 5A is: %d\n', hex2dec(A{indA5(i) + 4}) + hex2dec(A{indA5(i) + 5}))
end
end
Thankyou so much.. it works like a charm.. however is it possible not to add but combine the two term like
if the third term is 10 and 4th term is also 10 the required value be decimal equivalent of 1010=4112
sorry to bother you again but just wanted to ask can the final converted value be plotted against time?
you can combine 3rd and 4th terms as follows:
for i = 1:numel(loc)
if i ~= numel(loc) && loc(i) == 1 && difference(i) == 1
fprintf('The decimal equivalent of 3rd + 4th terms after A5 and 5A is: %d\n', hex2dec(strcat(A{indA5(i) + 4}, A{indA5(i) + 5})))
elseif loc(i) == 1
fprintf('The decimal equivalent of 3rd + 4th terms after A5 and 5A is: %d\n', hex2dec(strcat(A{indA5(i) + 4}, A{indA5(i) + 5})))
end
end
How you like to plot these values against time? and what will be the time in this case?
plotting it in graph against time starting from 1 to any value(till there is the data to plot.. Thankyou..
You can do it as follows:
count = 1;
for i = 1:numel(loc)
if i ~= numel(loc) && loc(i) == 1 && difference(i) == 1
arr(count) = hex2dec(strcat(A{indA5(i) + 4}, A{indA5(i) + 5}));
fprintf('The decimal equivalent of 3rd + 4th terms after A5 and 5A is: %d\n', arr(count))
count = count + 1;
elseif loc(i) == 1
arr(count) = hex2dec(strcat(A{indA5(i) + 4}, A{indA5(i) + 5}));
fprintf('The decimal equivalent of 3rd + 4th terms after A5 and 5A is: %d\n', arr(count))
end
end
plot(arr)
Wow.... Thankyou so much.. You've been a great help.. (y)
You can do it as follows:
ID = fopen('filename.txt');
A = textscan(ID, '%s');
fclose(ID);
A = A{:};
A = A{1};
count = 1;
for i = 1:2:length(A);
B{count} = A(i:i+1);
count = count + 1;
end
It showed the following error while running
Too many outputs requested. Most likely cause is missing [] around left hand side that has a comma separated list expansion.
Error in ==> Final1 at 7 A = A{:};
my file is
Maybe you can try make it better this way:
ID = fopen('filename.txt');
A = textscan(ID, '%s');
fclose(ID);
A = cell2mat(A{:});
count = 1;
for i = 1:2:length(A);
B{count} = A(i:i+1);
count = count + 1;
end
Also if the error remains then please share your code so that error could be understood correctly. Good luck!
Dear sixwwwwww, for the attached data file it showed the following error, while using the above given code.. Thankyou ..
I tried the same code with the data you provided and I didn't get any error. Can you show me your complete code?
clear all;
% Read file in the form of string
ID = fopen('sinuecg.txt');
A = textscan(ID,'%s');
fclose(ID);
% Your array
A = A{:};
% Find the locations of bytes 'A5' within array
indA5 = find(ismember(A, 'A5'));
% Find the locations of bytes '5A' within array
ind5A = find(ismember(A, '5A'));
% Find whether all 'A5' and '5A' located consecutively
if numel(indA5) > numel(ind5A) && indA5(end) < numel(A)
for i = 1:numel(indA5)
loc(i) = strcmp(A{indA5(i) + 1}, '5A');
end
elseif numel(indA5) < numel(ind5A) && ind5A(end) < numel(A)
for i = 1:numel(ind5A)
loc(i) = strcmp(A{ind5A(i) - 1}, 'A5');
end
else
loc = ind5A - indA5 == 1;
end
% Find the difference in locations of two consectuve occurances of 'A5' and
% if the difference is 17 then stores 1 in variable 'difference' otherwise
% store '0'
difference = indA5(2:numel(indA5)) - indA5(1:numel(indA5) - 1) == 17;
count = 1;
for i = 1:numel(loc)
if i ~= numel(loc) && loc(i) == 1 && difference(i) == 1
arr(count) = hex2dec(strcat(A{indA5(i) + 4}, A{indA5(i) + 5}));
%fprintf('The decimal equivalent of 3rd + 4th terms after A5 and 5A is: %d\n', arr(count))
count = count + 1;ind5A;
elseif loc(i) == 1
arr(count) = hex2dec(strcat(A{indA5(i) + 4}, A{indA5(i) + 5}));loc;
%fprintf('The decimal equivalent of 3rd + 4th terms after A5 and 5A is: %d\n', arr(count))
end
end
Fs = 256; %Total samples in one second
Ts = 1/Fs; %Calculation of Time interval of sampling
t = 0:Ts:1-Ts; %sampling period
subplot(1,1,1), plot(arr);
xlabel('time (seconds)');
ylabel('amplitude');
title('ECG wave');
grid;
this should give sinusoidal waveform output..
THHANKYOU SIXWWWWWW
the error is ?? Error using ==> textscan Buffer overflow (bufsize = 4095) while reading string from file (row 1, field 1). Use 'bufsize' option. See HELP TEXTSCAN.
Error in ==> F at 4 A = textscan(ID, '%s');
here the problem is with the buffer size. So you can increase the buffer size as follows:
data = textscan(ID, '%s', 'BufSize', 10000);
This error is not because of code but because of buffer size(simply memory size) in your computer. You can try to increase buffer size as I described above
I have tried Increasing the memory size also but still the problem persists the code and the file is attached with it please help..
Thank you

Sign in to comment.

More Answers (1)

I know you accepted sixwwwwwwwwww's answer so I guess you have it solved already but it's not the way I would have done it at all. Way too complicated. I'd just read in the bytes with fread(), and simply extract the bytes you need with simple indexing, like this:
folder = 'C:\Users\Prabhav\Documents\Temporary';
fullFileName = fullfile(folder, 'hex.txt');
fid = fopen(fullFileName, 'rt');
numberOfBytesToRead = 2*(17+2) + 2*6
chars = fread(fid, numberOfBytesToRead, 'char')
fclose(fid);
% Extract 17th and 18th hex numbers
chars17and18 = chars(35:38)
fprintf('%c%c%c%c\n', chars17and18)
% Let's see it as characters in the command window:
char(chars17and18) % should show A55A if file is good.
% Now he wants to "display the 5th and 6th byte starting from A5 and 5A."
% This is not really clear if it's from the start of the A55A,
% or starting from the first byte after that, but I'll assume he wants the
% 23 and 24th bytes.
chars23and24 = chars(47:50)
fprintf('%c%c%c%c\n', chars23and24)
% Let's see it as characters in the command window:
char(chars23and24)
I know it looks longer and more complicated but that's just because there are comments and lines to display the bytes for you to look at them. The real main code is just the fread() line.

7 Comments

i've also attached the file from where information is to be extracted.. the fifth and sixth byte to display is starting from A5 and 5A, i mean 3rd set of data after each 5A.
ACKNOWLEDGEMENT
Image Analyst
Each hex number is 2 bytes, for example A5 - that's an "A" which is one byte, and a "5" which is another byte. So 17 hex numbers would be 2*17 so we need to skip past those. Then we need to take the 2 numbers starting after the 17th. So that's how I get 2*(17+2). Then you need to take 6 extra numbers because you need to get the 5th and 6th number so I add on 2*6 bytes to make sure I read those in. No messing with cell arrays or for loops or anything - just a simple and clean call to fread.
Dear Image Analyst, I think each hex number is equivalent to 4 bit(half byte) and thus A5 represents 1 byte. See for example: http://en.wikipedia.org/wiki/Hexadecimal. Because hex has base 16 = 2^4 so only 4 bits are required for one hex number and so two hex numbers make one byte.
Um.. that is a neat logic, however that would not conform the occurance of A55A is always after 17 bytes so if it is after less than 17 bytes then we need to discard those set of 5th and 6th (which is 4 extra numbers). will the same set of code work for this as well?
Thankyou
Yes, but he has a text file, not a binary file. What you say would be true if it were a binary file, but it's not - it's a text file. So the nibbles are actually taking up one whole ASCII character, 8 bits, one byte. So a hex number like A5 takes up two ASCII characters or two bytes, not one.
Not quite sure what you mean. I thought it was right after 17 hex numbers, so it would be the 18th and 19th number, if it were there, though if it's not there the 18th and 19th number would be something else. Of course you can just modify my code to look anywhere for the A5 using find().
folder = 'C:\Users\prabhav\Documents\Temporary';
fullFileName = fullfile(folder, 'hex.txt');
fid = fopen(fullFileName, 'rt');
% Define the max location where you would expect to find it, it it were there.
numberOfBytesToRead = 500;
chars = fread(fid, [1, numberOfBytesToRead], 'char');
fclose(fid);
% Find A55A (occurs in multiple places in this file).
lookingFor = 'A55A' - 0;
startingLocations = strfind(chars, lookingFor)
Actually i meant the data set of 17 bytes that i'd need to evaluate will always start with A55A and should not have another A55A amongts the bytes, however the data set i'd need to plot is 5th and 6th byte within the 17 bytes if A5 is 1st byte and 5A is 2nd Byte. so the problem is to find the 5th and 6th byte in the 17 byte data after finding the 17 byte data starting from A55A
Thankyou
ACKNOWLEDGEMENT
sixwwwwww
Image Analyst

Sign in to comment.

Categories

Asked:

on 31 Oct 2013

Commented:

on 4 Nov 2013

Community Treasure Hunt

Find the treasures in MATLAB Central and discover how the community can help you!

Start Hunting!