2

Hello and a happy new year,

I'm working on a kernel-module. It is necessary to do a numeric calculation of some parameter to set up the device correctly. The function works perfectly but the gcc compiler (I'm using kbuild) gives me the warning:

warning: the frame size of 1232 bytes is larger than 1024 bytes [-Wframe-larger-than=]

If I'm right this means that space local variables exceed a limitation given by the machine the module compiled on.

There are some questions now:

  1. Does this warning refer to the whole memory space needed for the module, this explicit function or this function and its sub-functions?
  2. How critical is this?
  3. I don't see a way to reduce the needed memory. Are there some suggestions to handle this? Any how-to?

Maybe it is helpful: The calculation uses a 64bit fixed-point-arithmetic. All the functions of this library are inline functions.

Thanks in advance

Alex


Following the advice from @Tsyvarev the problem could reduce to the allocation in a function as this example shows (I know that the code doesn't make sense - it's only for showing how I declare the variables inside the functions):

uint8_t getVal ( uint8_t )
{
  uint64_t ar1[128] = {0};
  uint64_t ar2[128] = {0};
  uint8_t val;

  // a much of stuff

  return val;
}

void fun ( void )
{
  uint64_t ar1[128] = {0};
  uint64_t ar2[128] = {0};
  uint8_t cnt;

  for(cnt=0; cnt<128; cnt++)
  {
    ar1[cnt] = getVal(cnt);
    ar1[cnt] = getVal(cnt);
  }
}
Alex44
  • 3,597
  • 7
  • 39
  • 56
  • 3
    Stack size for kernel's threads is 8 Kbytes only, so having function which consumes 1 Kbyte of stack is not good. General way for reduce stack consumption is storing data on heap instead of stack. – Tsyvarev Jan 07 '16 at 16:59
  • 1
    @Tsyvarev thanks for the good answer. I don't understand why someone think it is necessary to put my question on hold. The code which cause this is to big and not realizable with a small example. So I try to describe this behaviour and I think this makes more sense and is more clear. – Alex44 Jan 07 '16 at 20:42
  • 1
    As I saw, some Close Votes have been agains "Too broad" reason: there are generally **too many ways** for reduce stack usage. If you want advice for your particular case, you need to **provide code**, which you want to optimize. Of course, as your code could be large, it is OK to provide some part of it for purpose to optimize only this part. But this part should be *self-sufficient* in some way (see link in the reason's description). **Your current explanations are not sufficient.** – Tsyvarev Jan 07 '16 at 21:04
  • So what is a problem to store your `arr` arrays on heap instead of stack? – Tsyvarev Jan 07 '16 at 23:13
  • No problem. As you suggest I now use `kmalloc` to store the `arr` to the heap. Earlier I doesn't see this. I really want to thank you for your help with a "solved". But I can't. – Alex44 Jan 07 '16 at 23:17

1 Answers1

3

to point 3:

As suggested the solution is to store the data to the heap with kmalloc instead to the stack.

uint8_t getVal ( uint8_t )
{
  uint64_t *ar1;
  uint64_t *ar2;
  uint8_t val, cnt;

  // allocate memory on the heap
  ar1 = kmalloc(sizeof(uint64_t), 128);
  ar2 = kmalloc(sizeof(uint64_t), 128);

  // initialize the arrays
  for(cnt=0; cnt<128; cnt++)
  {
    ar1[cnt] = 0;
    ar2[cnt] = 0;
  }

  // a much of stuff

  return val;
}

void fun ( void )
{
  uint64_t *ar1;
  uint64_t *ar2;
  uint8_t cnt;

  // allocate memory on the heap
  ar1 = kmalloc(sizeof(uint64_t), 128);
  ar2 = kmalloc(sizeof(uint64_t), 128);

  // initialize the arrays
  for(cnt=0; cnt<128; cnt++)
  {
    ar1[cnt] = 0;
    ar2[cnt] = 0;
  }

 for(cnt=0; cnt<128; cnt++)
  {
    ar1[cnt] = getVal(cnt);
    ar1[cnt] = getVal(cnt);
  }
}
Alex44
  • 3,597
  • 7
  • 39
  • 56
  • Am I correct in saying kmalloc now works differently? Now it should be the size `sizeof(uint64_t) * 128` as the first argument and then some `gfp_t` flag as the second argument? – wxz Mar 31 '21 at 20:45
  • Yes, the second argument to those kmalloc()'s should be a gfp_t, probably GFP_KERNEL. Also, the code should be checking the return value from kmalloc() (though a kmalloc of that size will rarely fail), and there should be corresponding kfree()s before the functions return. Note that kmalloc(.,GFP_KERNEL) may sleep. – Bruce Fields Sep 23 '21 at 21:11