title: Redefining function from standard library
body: <p>Context: In a recent conversation, the question "does gcc/clang do <code>strlen("static string")</code> at compile time?" came up. After some testing, the answer seems to be yes, regardless the level of optimization. I was a bit surprised to see this done even at <code>-O0</code>, so I did some testing, and eventually arrived to the following code:</p>
  
  <pre><code>#include &lt;stdio.h&gt;
  
  unsigned long strlen(const char* s) {
    return 10;
  }
  
  unsigned long f() {
    return strlen("abcd");
  }
  
  unsigned long g(const char* s) {
    return strlen(s);
  }
  
  int main() {
    printf("%ld %ld\n",f(),g("abcd"));
    return 0;
  }
  </code></pre>
  
  <p>To my surprise, it prints <code>4 10</code> and not <code>10 10</code>. I tried compiling with <code>gcc</code> and <code>clang</code>, and with various flags (<code>-pedantic</code>, <code>-O0</code>, <code>-O3</code>, <code>-std=c89</code>, <code>-std=c11</code>, ...) and the behavior is consistent between the tests.</p>
  
  <p>Since I didn't include <code>string.h</code>, I expected my definition of <code>strlen</code> to be used. But the assembly code shows indeed that <code>strlen("abcd")</code> was basically replaced by <code>return 4</code> (which is what I'm observing when running the program).</p>
  
  <p>Also, the compilers print no warnings with <code>-Wall -Wextra</code> (more precisely, none related to the issue: they still warn that parameter <code>s</code> is unused in my definition of <code>strlen</code>).</p>
  
  <p>Two (related) questions arise (I think they are related enough to be asked in the same question):<br>
   - is it allowed to redefine a standard function in C when the header declaring it isn't included?<br>
   - does this program behave as it should? If so, what happens exactly?</p>