Hi,
I've found with my compiler, that when a function contains const
data in a function, that data is first copied to the stack[1].
Given:
/* Example 1 */
char Buffer[1024];
void My_Func(void)
{
const char TEXT[] = {'H', 'e', 'l', 'l', 'o', '\0'};
memcpy(Buffer, TEXT, sizeof(TEXT));
return;
}
My compiler copies the data in TEXT to some memory location,
then passes a pointer to that location to the memcpy routine.
If I move the declaration to outside of the function:
/* Example 2 */
const char TEXT[] = {'H', 'e', 'l', 'l', 'o', '\0'};
void My_Func(void)
{
memcpy(Buffer, TEXT, sizeof(TEXT));
return;
}
or label it as static (and keep it in the function):
/* Example 3 */
void My_Func(void)
{
static const char TEXT[] = {'H', 'e', 'l', 'l', 'o', '\0'};
memcpy(Buffer, TEXT, sizeof(TEXT));
return;
}
then the compiler passes a pointer to the text to memcpy,
without making an interim copy.
Here are my questions:
Q1: Is the interim duplication mandated by the C language
specification or is this a problem with my compiler?
Q2: Is the _static_ modifier supposed to have this effect?
Q3: My understanding is that constant data is placed into
a constant area and not copied. Am I wrong?
I'm working on an embedded system and I don't want a duplicate
copy of the data created. In our system, we've replaced
memcpy with memcpy_byte (our proprietary function) and we don't
want the library version invoked, which is what the compiler
does in Example 2.
------
[1] Yes, I know that the standard doesn't require implementations
to have a stack, call it read/write memory if "stack" bothers
you.
--
Thomas Matthews
C++ newsgroup welcome message: http://www.slack.net/~shiva/welcome.txt
C++ Faq: http://www.parashift.com/c++-faq-lite
C Faq: http://www.eskimo.com/~scs/c-faq/top.html
alt.comp.lang.l earn.c-c++ faq: http://www.raos.demon.uk/acllc-c++/faq.html
Other sites: http://www.josuttis.com -- C++ STL Library book 3 1753
Thomas Matthews wrote: I've found with my compiler, that when a function contains const data in a function, that data is first copied to the stack[1].
Given: /* Example 1 */ char Buffer[1024];
void My_Func(void) { const char TEXT[] = {'H', 'e', 'l', 'l', 'o', '\0'};
This instructs the compiler to create an automatic variable of type
"array of 6 char". If instead of calling "memcpy", you were passed
the address of this function to another function defined elsewhere
then the compiler would have no way of knowing that there is only one
copy of TEXT active at any time, so it would be obliged
#include <stdio.h>
void My_Func(void);
void function(const char *text)
{
static const char *saved;
if (!saved) {
saved = text;
My_Func();
}
else {
printf("Second call: %d %s %s\n", saved == text, saved, text);
}
}
void My_Func(void)
{
const char TEXT[] = {'H', 'e', 'l', 'l', 'o', '\0'};
function(TEXT);
}
int main()
{
My_Func();
return 0;
}
The output of this program is:
Second call: 0 Hello Hello
The second time 'function' is called, the pointers 'saved' and 'text'
each point to a valid, active variable called 'TEXT', one in each
active invocation of 'My_Func'. The C standard requires that these
two variables have distinct addresses, so the compiler is obliged to
create two copies.
memcpy(Buffer, TEXT, sizeof(TEXT));
Since memcpy() is a standard function, the compiler has special
knowledge; it knows that memcpy() doesn't capture the value of the
source pointer and that it doesn't invoke 'My_Func' recursively, so it
could legitimately create only a single, static copy of 'TEXT' as an
optimization. As it happens, that optimization is entirely
unnecessary, because there are at least two ways for the programmer to
indicate that only a single copy is desired. Both involve objects
with static storage duration:
void My_Func(void)
{
const char *TEXT = "Hello";
This creates an unamed static array of char and assigns the address of
the first element to the variable 'TEXT'.
void My_Func(void)
{
static const char TEXT[] = {'H', 'e', 'l', 'l', 'o', '\0'};
This creates a named array of char with static storage duration. In
both of these cases there is only one object involved, and there is no
reason for any compiler to make unwanted copies. I think that answers
all of your questions, but just to be clear:
Here are my questions: Q1: Is the interim duplication mandated by the C language specification or is this a problem with my compiler?
No. The duplication is mandated unless the compiler can prove that
there is no way for a strictly conforming program to tell whether or
not a copy was made.
Q2: Is the _static_ modifier supposed to have this effect?
Yes.
Q3: My understanding is that constant data is placed into a constant area and not copied. Am I wrong?
Yes.
Jeremy.
Thomas Matthews wrote: I've found with my compiler, that when a function contains const data in a function, that data is first copied to the stack[1].
Given: /* Example 1 */ char Buffer[1024];
void My_Func(void) { const char TEXT[] = {'H', 'e', 'l', 'l', 'o', '\0'};
This instructs the compiler to create an automatic variable of type
"array of 6 char". If instead of calling "memcpy", you were to pass
the address of TEXT to another function defined elsewhere then the
compiler, with no way of knowing that there is only one active copy
accessible at any time, would be obliged to actually allocate a new
variable on each call to the function.
#include <stdio.h>
void My_Func(void);
void function(const char *text)
{
static const char *saved;
if (!saved) {
saved = text;
My_Func();
}
else {
printf("Second call: %d %s %s\n", saved == text, saved, text);
}
}
void My_Func(void)
{
const char TEXT[] = {'H', 'e', 'l', 'l', 'o', '\0'};
function(TEXT);
}
int main()
{
My_Func();
return 0;
}
The output of this program is:
Second call: 0 Hello Hello
The second time 'function' is called, the pointers 'saved' and 'text'
each point to a valid, active variable called 'TEXT', one in each
active invocation of 'My_Func'. The C standard requires that these
two variables have distinct addresses, so the compiler is obliged to
create two copies.
memcpy(Buffer, TEXT, sizeof(TEXT));
Since memcpy() is a standard function, the compiler has special
knowledge; it knows that memcpy() doesn't capture the value of the
source pointer and that it doesn't invoke 'My_Func' recursively, so it
could legitimately create only a single, static copy of 'TEXT' as an
optimization. As it happens, that optimization is entirely
unnecessary, because there are at least two ways for the programmer to
indicate that only a single copy is desired. Both involve objects
with static storage duration:
void My_Func(void)
{
const char *TEXT = "Hello";
This creates an unamed static array of char and assigns the address of
the first element to the variable 'TEXT'.
void My_Func(void)
{
static const char TEXT[] = {'H', 'e', 'l', 'l', 'o', '\0'};
This creates a named array of char with static storage duration. In
both of these cases there is only one object involved, and there is no
reason for any compiler to make unwanted copies. I think that answers
all of your questions, but just to be clear:
Here are my questions: Q1: Is the interim duplication mandated by the C language specification or is this a problem with my compiler?
No. The duplication is mandated unless the compiler can prove that
there is no way for a strictly conforming program to tell whether or
not a copy was made.
Q2: Is the _static_ modifier supposed to have this effect?
Yes.
Q3: My understanding is that constant data is placed into a constant area and not copied. Am I wrong?
Yes.
Jeremy.
Thomas Matthews <Th************ *************** *@sbcglobal.net > wrote: Here are my questions: Q1: Is the interim duplication mandated by the C language specification or is this a problem with my compiler?
Neither. The compiler is at liberty to treat such an array as if it
were static (because any attempt to modify it results in undefined
behavior), but is under no obligation to do so, nor would most
programmers expect it to.
Q2: Is the _static_ modifier supposed to have this effect?
Yes. Conceptually, automatic variables are created (and initialized)
each time the containing block is entered and destroyed when the block
is exited; static variables are conceptually created at program startup
and destroyed at program end. Your compiler (like most compilers) is
implementing this concept literally -- allocating space (on the stack)
each time the block is entered and initializing it to the correct
values even though this particular automatic variable is declared const.
Q3: My understanding is that constant data is placed into a constant area and not copied. Am I wrong?
Yes. Defining an object as const simply indicates that you do not
intend to modify it. It does not oblige the compiler to prevent you
from modifying it or to perform optimizations based on it not being
modifiable.
-Larry Jones
He just doesn't want to face up to the fact that I'll be
the life of every party. -- Calvin This thread has been closed and replies have been disabled. Please start a new discussion. Similar topics |
by: pvinodhkumar |
last post by:
The number of elemets of the array, the array bound must be constant
expression?Why is this restriction?
Vinodh
|
by: Thomas Matthews |
last post by:
Hi,
I've found with my compiler, that when a function contains const
data in a function, that data is first copied to the stack.
Given:
/* Example 1 */
char Buffer;
void My_Func(void)
|
by: Thomas L. |
last post by:
Hi all,
Does a "NULL constant function" exist in C? I mean:
I am searching for a C language constant which would be something like
a function but which would be translated by a compiler into "nothing":
no argument push in the stack pointer, no execution of the function
instructions, no cleaning up, nothing, nada, rien, vide...
I could then initialize a function pointer f to that constant function
and ask
(*f)(any_argument_list)
|
by: ravinderthakur |
last post by:
hi all experts,
i have a structure with the constant memebers such as one given below:
typedef struct {
const int cbcode;
int cberror;
} xtsetplatestaterec;
|
by: Moger |
last post by:
This is a two parte
1. What to the performance differnace between a Class and a struct. I have a handler class which has a list containing a lot of instances of a class which purely holds data, All the operations are caried out within the handler, would I be better to use a strut instead
2. I want to extact the data from the data holder class / struct, using the hander class archive the data away into a byte steam to either place in a...
| |
by: John Friedland |
last post by:
My problem: I need to call (from C code) an arbitrary C library
function, but I don't know until runtime what the function name is,
how many parameters are required, and what the parameters are. I can
use dlopen/whatever to convert the function name into a pointer to
that function, but actually calling it, with the right number of
parameters, isn't easy.
As far as I can see, there are only two solutions:
1) This one is portable. If...
|
by: Arpan |
last post by:
The .NET Framework 2.0 documentation states that
An Object variable always holds a pointer to the data, never the data
itself.
Now w.r.t. the following ASP.NET code snippet, can someone please
explain me what does the above statement mean?
<script runat="server">
Class Clock
|
by: Brad Pears |
last post by:
I am using a function called "CreateSQLParam" which adds SQL parameters to a
collection.
The function is shown below... I add a parameter to a collection using the
following line code...
------------------------------------------------------------------------------------
dim vcContractNo as varchar
dim colParms as collection
vcContractNo = "07-00001"
|
by: jacob navia |
last post by:
Abstract:
Continuing the discussion about abstract data types, in this
discussion group, a string collection data type is presented,
patterned after the collection in C# and similar languages (Java).
It stores character strings, and resizes itself to accommodate
new strings when needed.
Interface:
----------
|
by: Oralloy |
last post by:
Hello folks,
I am unable to find appropriate documentation on the type promotion of bit-fields when using the generalised comparison operator "<=>".
The problem is that using the GNU compilers, it seems that the internal comparison operator "<=>" tries to promote arguments from unsigned to signed.
This is as boiled down as I can make it.
Here is my compilation command:
g++-12 -std=c++20 -Wnarrowing bit_field.cpp
Here is the code in...
|
by: Hystou |
last post by:
Overview:
Windows 11 and 10 have less user interface control over operating system update behaviour than previous versions of Windows. In Windows 11 and 10, there is no way to turn off the Windows Update option using the Control Panel or Settings app; it automatically checks for updates and installs any it finds, whether you like it or not. For most users, this new feature is actually very convenient. If you want to control the update process,...
| |
by: tracyyun |
last post by:
Dear forum friends,
With the development of smart home technology, a variety of wireless communication protocols have appeared on the market, such as Zigbee, Z-Wave, Wi-Fi, Bluetooth, etc. Each protocol has its own unique characteristics and advantages, but as a user who is planning to build a smart home system, I am a bit confused by the choice of these technologies. I'm particularly interested in Zigbee because I've heard it does some...
|
by: agi2029 |
last post by:
Let's talk about the concept of autonomous AI software engineers and no-code agents. These AIs are designed to manage the entire lifecycle of a software development project—planning, coding, testing, and deployment—without human intervention. Imagine an AI that can take a project description, break it down, write the code, debug it, and then launch it, all on its own....
Now, this would greatly impact the work of software developers. The idea...
|
by: conductexam |
last post by:
I have .net C# application in which I am extracting data from word file and save it in database particularly. To store word all data as it is I am converting the whole word file firstly in HTML and then checking html paragraph one by one.
At the time of converting from word file to html my equations which are in the word document file was convert into image.
Globals.ThisAddIn.Application.ActiveDocument.Select();...
|
by: TSSRALBI |
last post by:
Hello
I'm a network technician in training and I need your help.
I am currently learning how to create and manage the different types of VPNs and I have a question about LAN-to-LAN VPNs.
The last exercise I practiced was to create a LAN-to-LAN VPN between two Pfsense firewalls, by using IPSEC protocols.
I succeeded, with both firewalls in the same network. But I'm wondering if it's possible to do the same thing, with 2 Pfsense firewalls...
|
by: adsilva |
last post by:
A Windows Forms form does not have the event Unload, like VB6. What one acts like?
|
by: 6302768590 |
last post by:
Hai team
i want code for transfer the data from one system to another through IP address by using C# our system has to for every 5mins then we have to update the data what the data is updated we have to send another system
| |
by: muto222 |
last post by:
How can i add a mobile payment intergratation into php mysql website.
| |