Skip to content

os: MkdirAll using both Stat and Lstat #80511

Description

@zhangyoufu

Go version

go version go1.26.4 darwin/arm64

Output of go env in your module/workspace:

<omitted>

What did you do?

os.MkdirAll was introduced in commit 66f5e89. Where both the fast path and slow path used Lstat.

To fix issue #1149, https://golang.org/cl/3564041 modified the fast path to use Stat instead of Lstat. However, the slow path was left unmodified and still using Lstat.

There is a potential race between os.MkdirAll and symlink to directory created by external actor. In the slow path of os.MkdirAll, when Mkdir returned EEXIST, Lstat on a symlink to directory, the check dir.IsDir() failed, and EEXIST is returned from MkdirAll.

Reproducer: https://go.dev/play/p/n8CPIyX3_Ty

I suggest that we should use Stat instead of Lstat in MkdirAll for consistency.

What did you see happen?

2009/11/10 23:00:00 mkdir foo: file exists
2009/11/10 23:00:00 mkdir foo: file exists
2009/11/10 23:00:00 mkdir foo: file exists

What did you expect to see?

empty log

Metadata

Metadata

Assignees

No one assigned

    Labels

    NeedsInvestigationSomeone must examine and confirm this is a valid issue and not a duplicate of an existing one.

    Type

    No type

    Projects

    No projects

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions