|  support |  documentation |  report a bug |  advanced search |  search howto |  statistics |  random bug |  login
Bug #67220 realpath() on MacOSX doesn't normalize the case of characters
Submitted: 2014-05-06 15:24 UTC Modified: 2015-08-10 20:24 UTC
Avg. Score:4.3 ± 0.5
Reproduced:3 of 3 (100.0%)
Same Version:2 (66.7%)
Same OS:3 (100.0%)
From: nicolas dot grekas+php at gmail dot com Assigned:
Status: Re-Opened Package: Filesystem function related
PHP Version: 5.5.12 OS: MacOSX/Darwin
Private report: No CVE-ID: None
Have you experienced this issue?
Rate the importance of this bug to you:

 [2014-05-06 15:24 UTC] nicolas dot grekas+php at gmail dot com
See test script.

__FILE__, __DIR__, ReflectionClass::getFilename(), etc. are also affected (but getcwd() is OK).

Test script:

var_dump(realpath('/Users') === realpath('/users'));

Expected result:

Actual result:


Add a Patch

Pull Requests

Add a Pull Request


AllCommentsChangesGit/SVN commitsRelated reports
 [2014-05-07 14:58 UTC]
-Status: Open +Status: Not a bug
 [2014-05-07 14:58 UTC]
Almost certainly this is because HFS+ is case-sensitive by default. Currently realpath "expands all symbolic links and resolves references to '/./', '/../' and extra '/' characters in the input path and returns the canonicalized absolute pathname".

Nowhere does that indicate anything about case sensitivity.
 [2014-05-07 15:06 UTC]
Well, I am still somewhat sympathetic to this though. The native OSX realpath() call does normalize the case. eg.

#include <stdio.h>
#include <stdlib.h>

int main(int argc, char **argv) {
        printf("%s %s\n",realpath("/Users",NULL),realpath("/users",NULL));

Outputs: /Users /Users

And we used to do so as well when we relied on the system-level realpath() call. However, after we optimized realpath() to allow us to do intra-path caching, we now use our own implementation.

Fixing this particular issue isn't that easy, and you are right, we don't promise to do path normalization in this function.
 [2014-05-07 15:14 UTC] nicolas dot grekas+php at gmail dot com
The doc says "returns the canonicalized absolute pathname"

"canonicalized" is what makes this a bug.

An other example that fails is require_once:

require_once 'TEST.PHP';
require_once 'test.php';

This does require the same file twice.
 [2014-05-07 18:10 UTC]
for the record HFS+ is optionally supports case sensitivity, but the current default is the case insensitive/preserve mode AFAIK.
I don't have a windows box at hand at the moment, but I'm fairly sure that realpath on windows does indeed correctly canonizes the path ( seems to be confirming this).

I think closing the issue with Not a bug is wrong, we should either keep it open until we can fix it, or mark as Won't fix, and document it.
 [2014-08-01 10:41 UTC] rullaf at gmail dot com
Please note this is sill an issue. Either the documentation should be changed to warn the realpath function does NOT return canonical path (it currently says `realpath — Returns canonicalized absolute pathname`) or the function should be fixed.
 [2015-08-04 15:06 UTC]
I agree with tyrael: "I think closing the issue with Not a bug is wrong, we should either keep it open until we can fix it, or mark as Won't fix, and document it."

Side note, jpauli talks about the intra-path caching rasmus mentioned in this article:
 [2015-08-05 14:25 UTC]
-Status: Not a bug +Status: Re-Opened
 [2015-08-05 15:09 UTC]
Automatic comment from SVN on behalf of cmb
Log: added note regarding normalization of the character case on case-insensitive
filesystems (see #67220)
 [2015-08-05 15:26 UTC] andreas at heigl dot org
Has this issue been tested with both case-sensitive AND case-insensitive HFS+ and are the results the same?

Or is it only an issue with case-insensitive HFS+?
 [2015-08-10 20:24 UTC]
on case-sensitive HFS there is no issue, as there is nothing to "normalize".
HFS+ by default is case-insensitive case-preserving, the same as NTFS on windows by default.
given how we support returning the preserved version of the filename on Windows/NTFS and the fact that the realpath libc function on mac seems to properly return the preserved version(used to test it) I think it would be expected to work that way from php also.
PHP Copyright © 2001-2022 The PHP Group
All rights reserved.
Last updated: Thu Oct 06 17:05:51 2022 UTC