- Community Home
- >
- Servers and Operating Systems
- >
- Operating Systems
- >
- Operating System - HP-UX
- >
- assigning a long long to a long
Categories
Company
Local Language
Forums
Discussions
Forums
- Data Protection and Retention
- Entry Storage Systems
- Legacy
- Midrange and Enterprise Storage
- Storage Networking
- HPE Nimble Storage
Discussions
Forums
Discussions
Discussions
Discussions
Forums
Discussions
Discussion Boards
Discussion Boards
Discussion Boards
Discussion Boards
- BladeSystem Infrastructure and Application Solutions
- Appliance Servers
- Alpha Servers
- BackOffice Products
- Internet Products
- HPE 9000 and HPE e3000 Servers
- Networking
- Netservers
- Secure OS Software for Linux
- Server Management (Insight Manager 7)
- Windows Server 2003
- Operating System - Tru64 Unix
- ProLiant Deployment and Provisioning
- Linux-Based Community / Regional
- Microsoft System Center Integration
Discussion Boards
Discussion Boards
Discussion Boards
Discussion Boards
Discussion Boards
Discussion Boards
Discussion Boards
Discussion Boards
Discussion Boards
Discussion Boards
Discussion Boards
Discussion Boards
Discussion Boards
Discussion Boards
Discussion Boards
Discussion Boards
Discussion Boards
Discussion Boards
Discussion Boards
Discussion Boards
Community
Resources
Forums
Blogs
- Subscribe to RSS Feed
- Mark Topic as New
- Mark Topic as Read
- Float this Topic for Current User
- Bookmark
- Subscribe
- Printer Friendly Page
- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
04-22-2006 02:31 AM
04-22-2006 02:31 AM
assigning a long long to a long
I have a code that reads a data from a binary file which can be 8 byte long or 4 byte long (based on where it was saved, if it was saved on a 64bit host, it will have 8 byte long data, other wise 4 byte). So I use the following code
readBigValue(long long *bval)
{
long long lval = 0;
size_t = m_pHeader->size_to_read;
fread(&lval, size, 1, m_pFile);
if(m_bSwap)
Swap(lval);
long val = (long)lval;
*bval = lval;
#ifdef _DEBUG
fprintf(stderr, "read val: %d\n", val);
#endif
}
The output I get is 0. If I use an array of 2 long and manage with either varr[0] or varr[1]
(based on the endianness) it is fine
Can you please advise me how to handle a situation like this
TIA
Satya
- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
04-22-2006 09:47 AM
04-22-2006 09:47 AM
Re: assigning a long long to a long
size_t = m_pHeader->size_to_read;
I suspect that you meant
size_t size = ...
There are several things wrong:
1) You are trying to transfer binary data from 1 platoform to another; in addition to size and endianess, there is another aspect you are not considering and that is data alignment. I suspect that is why arrays work but plain longs do not.
In any event you are going about this is in a more or less Mickey Mouse way. What you should be doing is writing and reading the data in XDR (external data representation) format. The XDR library routines take care of byte-swappping, size, alignment, and endianess automatically because the #defines are instantiated when the machine-specific library code is compiled. All you have to do is use the functions and XDR takes carew of the rest. The good news is that if you port to another platform or OS, nothingh will have to change.
Man xdr, xdr_simple for details.
- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
04-23-2006 11:09 PM
04-23-2006 11:09 PM
Re: assigning a long long to a long
Although I have to aggree with you in theory, XDR on both ends would be a better method, in the Real World sometimes you cannot control both ends of the data flow. I routinely get handed a new input file specification (from a COTS program) and get told they we are going to be getting files in this format next week and the users need the data the next day (or the same day). So a new filter has to be generated to convert the file format into what we use internally.
Satya:
I see a couple of things wrong with your code. To start with though, you should post a complete, compilable, expample of the problem, cut-and-pasted into the posting not re-typed. This is so that the folks you are asking for help can test the code themselves if they are so imclinded to do so. The most glaring problem with the above I can see is:
if(m_bSwap)
Swap(lval);
This does not return/alter anything in the calling function. The value of lval is copied and, I assume from the function's name, byte swapped in the Swap function. But C *always* uses call by value, so a **copy** of lval is byte swapped and nothing is altered in the readBigValue function. You either need to pass the address of lval to Swap, or return the swapped value back from Swap.
Example (return value):
if (m_bSwap)
lval = Swap(lval);
or, for the address version:
if (m_bSwap)
Swap(&lval);
Either way the definition of the Swap function will have to be changed and probably some of the code within. Of the two, I would probably go with the return a long long version, but it's doable either way.
- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
04-24-2006 09:26 PM
04-24-2006 09:26 PM
Re: assigning a long long to a long
thanks for the information.
main(int argc, char **argv)
{
long val = 200;
long long big_val = 0;
long pval;
FILE *fp = NULL;
fp = fopen("test1", "wb");
fwrite(&val, sizeof(long), 1, fp);
fclose(fp);
fp = fopen("test1", "rb");
fread(&big_val, sizeof(long), 1, fp);
/*
pp = (unsigned int *)&big_val;
pval = (pp[0]) ? pp[0] : pp[1];
*/
pval = big_val;
fclose(fp);
fprintf(stderr, "read value: %d\n", pval);
}
If I run the above program on linux, the output is 200, whereas it prints 0 on HP-UX, SUN and IBM.
I have to use the code in the comment to get proper assignment. Can you please suggest why is this beahviour?
TIA
Satya
- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
04-24-2006 11:01 PM
04-24-2006 11:01 PM
Re: assigning a long long to a long
Okay, I think I can understand what's going on, but since I am NOT a C expert some of this is guesswork, but educated guesswork.
First: in the code you posted you write out 4 bytes (a long) to the file. This is fine, but then you go back and read that 4 bytes back into a long long, 8 bytes in length. This read then places that 4 bytes into the *high order half* of the long long big_val variable.
Since the big_val variable now holds some large number, which will not fit into a normal int, the pval=big_val line simply copies the *low order half* of big_val into pval.
The reason the commented out code works is that you are accessing the 8 byte long long as if it were two seperate 4 byte long values, and your line: pval = (pp[0]) ? pp[0] : pp[1]; will grab whichever half of the long long that is non-zero, you get the correct result.
Clear as mud? I have attached a modification of your code to this post that might help explain things a bit. I am not a C expert, and I was in a bit of a hurry, so this is not my best code.
- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
04-25-2006 01:36 AM
04-25-2006 01:36 AM
Re: assigning a long long to a long
I return to my "correct" solution - XDR.
- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
04-25-2006 04:21 AM
04-25-2006 04:21 AM
Re: assigning a long long to a long
I aggree with you completely on the best solution. And my code, as you point out, is still flawed which I aggree with completely. There are times, though, when you cannot change the other end of the process to write XDR files, so I was attempting to point out a possible solution approach. That was the assumption I was proceeding on.
The problem is, and will continue to be, is that satya is attempting to read four bytes into an 8 byte variable. This will be read differently on a Big-endian and small-endian platforms. Always. XDR, or even just plain ASCII, is the best solution for this, but I was also trying to answer the question of "why does this not work".
Zero points for this one please.
- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
04-25-2006 06:43 PM
04-25-2006 06:43 PM
Re: assigning a long long to a long
I had to read the 4byte data into 8byte data type, because the input file might have come from a 64bit host. So I have done that "using the non-zero half" of the read 8byte data (only when I know that the data I am reading is just 4byte long).
Thanks again for the suggestion
Satya