Skip to content
Projeler
Gruplar
Parçacıklar
Yardım
Yükleniyor...
Oturum aç / Kaydol
Gezinmeyi değiştir
C
cpython
Proje
Proje
Ayrıntılar
Etkinlik
Cycle Analytics
Depo (repository)
Depo (repository)
Dosyalar
Kayıtlar (commit)
Dallar (branch)
Etiketler
Katkıda bulunanlar
Grafik
Karşılaştır
Grafikler
Konular (issue)
0
Konular (issue)
0
Liste
Pano
Etiketler
Kilometre Taşları
Birleştirme (merge) Talepleri
0
Birleştirme (merge) Talepleri
0
CI / CD
CI / CD
İş akışları (pipeline)
İşler
Zamanlamalar
Grafikler
Paketler
Paketler
Wiki
Wiki
Parçacıklar
Parçacıklar
Üyeler
Üyeler
Collapse sidebar
Close sidebar
Etkinlik
Grafik
Grafikler
Yeni bir konu (issue) oluştur
İşler
Kayıtlar (commit)
Konu (issue) Panoları
Kenar çubuğunu aç
Batuhan Osman TASKAYA
cpython
Commits
8f1a8e32
Kaydet (Commit)
8f1a8e32
authored
May 28, 2013
tarafından
Jason R. Coombs
Dosyalara gözat
Seçenekler
Dosyalara Gözat
İndir
Sade Fark
Merge with 3.3
üst
667a03b2
3a092867
Hide whitespace changes
Inline
Side-by-side
Showing
3 changed files
with
168 additions
and
13 deletions
+168
-13
os.rst
Doc/library/os.rst
+5
-3
test_os.py
Lib/test/test_os.py
+36
-8
posixmodule.c
Modules/posixmodule.c
+127
-2
No files found.
Doc/library/os.rst
Dosyayı görüntüle @
8f1a8e32
...
@@ -2024,9 +2024,10 @@ features:
...
@@ -2024,9 +2024,10 @@ features:
Create a symbolic link pointing to *source* named *link_name*.
Create a symbolic link pointing to *source* named *link_name*.
On Windows, a symlink represents either a file or a directory, and does not
On Windows, a symlink represents either a file or a directory, and does not
morph to the target dynamically. If *target_is_directory* is set to ``True``,
morph to the target dynamically. If the target is present, the type of the
the symlink will be created as a directory symlink, otherwise as a file symlink
symlink will be created to match. Otherwise, the symlink will be created
(the default). On non-Window platforms, *target_is_directory* is ignored.
as a directory if *target_is_directory* is ``True`` or a file symlink (the
default) otherwise. On non-Window platforms, *target_is_directory* is ignored.
Symbolic link support was introduced in Windows 6.0 (Vista). :func:`symlink`
Symbolic link support was introduced in Windows 6.0 (Vista). :func:`symlink`
will raise a :exc:`NotImplementedError` on Windows versions earlier than 6.0.
will raise a :exc:`NotImplementedError` on Windows versions earlier than 6.0.
...
@@ -2042,6 +2043,7 @@ features:
...
@@ -2042,6 +2043,7 @@ features:
to the administrator level. Either obtaining the privilege or running your
to the administrator level. Either obtaining the privilege or running your
application as an administrator are ways to successfully create symlinks.
application as an administrator are ways to successfully create symlinks.
:exc:`OSError` is raised when the function is called by an unprivileged
:exc:`OSError` is raised when the function is called by an unprivileged
user.
user.
...
...
Lib/test/test_os.py
Dosyayı görüntüle @
8f1a8e32
...
@@ -686,13 +686,8 @@ class WalkTests(unittest.TestCase):
...
@@ -686,13 +686,8 @@ class WalkTests(unittest.TestCase):
f
.
write
(
"I'm "
+
path
+
" and proud of it. Blame test_os.
\n
"
)
f
.
write
(
"I'm "
+
path
+
" and proud of it. Blame test_os.
\n
"
)
f
.
close
()
f
.
close
()
if
support
.
can_symlink
():
if
support
.
can_symlink
():
if
os
.
name
==
'nt'
:
os
.
symlink
(
os
.
path
.
abspath
(
t2_path
),
link_path
)
def
symlink_to_dir
(
src
,
dest
):
symlink_to_dir
(
'broken'
,
broken_link_path
,
True
)
os
.
symlink
(
src
,
dest
,
True
)
else
:
symlink_to_dir
=
os
.
symlink
symlink_to_dir
(
os
.
path
.
abspath
(
t2_path
),
link_path
)
symlink_to_dir
(
'broken'
,
broken_link_path
)
sub2_tree
=
(
sub2_path
,
[
"link"
],
[
"broken_link"
,
"tmp3"
])
sub2_tree
=
(
sub2_path
,
[
"link"
],
[
"broken_link"
,
"tmp3"
])
else
:
else
:
sub2_tree
=
(
sub2_path
,
[],
[
"tmp3"
])
sub2_tree
=
(
sub2_path
,
[],
[
"tmp3"
])
...
@@ -1516,7 +1511,7 @@ class Win32SymlinkTests(unittest.TestCase):
...
@@ -1516,7 +1511,7 @@ class Win32SymlinkTests(unittest.TestCase):
os
.
remove
(
self
.
missing_link
)
os
.
remove
(
self
.
missing_link
)
def
test_directory_link
(
self
):
def
test_directory_link
(
self
):
os
.
symlink
(
self
.
dirlink_target
,
self
.
dirlink
,
True
)
os
.
symlink
(
self
.
dirlink_target
,
self
.
dirlink
)
self
.
assertTrue
(
os
.
path
.
exists
(
self
.
dirlink
))
self
.
assertTrue
(
os
.
path
.
exists
(
self
.
dirlink
))
self
.
assertTrue
(
os
.
path
.
isdir
(
self
.
dirlink
))
self
.
assertTrue
(
os
.
path
.
isdir
(
self
.
dirlink
))
self
.
assertTrue
(
os
.
path
.
islink
(
self
.
dirlink
))
self
.
assertTrue
(
os
.
path
.
islink
(
self
.
dirlink
))
...
@@ -1610,6 +1605,38 @@ class Win32SymlinkTests(unittest.TestCase):
...
@@ -1610,6 +1605,38 @@ class Win32SymlinkTests(unittest.TestCase):
shutil
.
rmtree
(
level1
)
shutil
.
rmtree
(
level1
)
@support.skip_unless_symlink
class
NonLocalSymlinkTests
(
unittest
.
TestCase
):
def
setUp
(
self
):
"""
Create this structure:
base
\
___ some_dir
"""
os
.
makedirs
(
'base/some_dir'
)
def
tearDown
(
self
):
shutil
.
rmtree
(
'base'
)
def
test_directory_link_nonlocal
(
self
):
"""
The symlink target should resolve relative to the link, not relative
to the current directory.
Then, link base/some_link -> base/some_dir and ensure that some_link
is resolved as a directory.
In issue13772, it was discovered that directory detection failed if
the symlink target was not specified relative to the current
directory, which was a defect in the implementation.
"""
src
=
os
.
path
.
join
(
'base'
,
'some_link'
)
os
.
symlink
(
'some_dir'
,
src
)
assert
os
.
path
.
isdir
(
src
)
class
FSEncodingTests
(
unittest
.
TestCase
):
class
FSEncodingTests
(
unittest
.
TestCase
):
def
test_nop
(
self
):
def
test_nop
(
self
):
self
.
assertEqual
(
os
.
fsencode
(
b
'abc
\xff
'
),
b
'abc
\xff
'
)
self
.
assertEqual
(
os
.
fsencode
(
b
'abc
\xff
'
),
b
'abc
\xff
'
)
...
@@ -2243,6 +2270,7 @@ def test_main():
...
@@ -2243,6 +2270,7 @@ def test_main():
Pep383Tests
,
Pep383Tests
,
Win32KillTests
,
Win32KillTests
,
Win32SymlinkTests
,
Win32SymlinkTests
,
NonLocalSymlinkTests
,
FSEncodingTests
,
FSEncodingTests
,
DeviceEncodingTests
,
DeviceEncodingTests
,
PidTests
,
PidTests
,
...
...
Modules/posixmodule.c
Dosyayı görüntüle @
8f1a8e32
...
@@ -6735,6 +6735,124 @@ check_CreateSymbolicLink()
...
@@ -6735,6 +6735,124 @@ check_CreateSymbolicLink()
return
(
Py_CreateSymbolicLinkW
&&
Py_CreateSymbolicLinkA
);
return
(
Py_CreateSymbolicLinkW
&&
Py_CreateSymbolicLinkA
);
}
}
void
_dirnameW
(
WCHAR
*
path
)
{
/* Remove the last portion of the path */
WCHAR
*
ptr
;
/* walk the path from the end until a backslash is encountered */
for
(
ptr
=
path
+
wcslen
(
path
);
ptr
!=
path
;
ptr
--
)
{
if
(
*
ptr
==
*
L"
\\
"
||
*
ptr
==
*
L"/"
)
{
break
;
}
}
*
ptr
=
0
;
}
void
_dirnameA
(
char
*
path
)
{
/* Remove the last portion of the path */
char
*
ptr
;
/* walk the path from the end until a backslash is encountered */
for
(
ptr
=
path
+
strlen
(
path
);
ptr
!=
path
;
ptr
--
)
{
if
(
*
ptr
==
'\\'
||
*
ptr
==
'/'
)
{
break
;
}
}
*
ptr
=
0
;
}
int
_is_absW
(
WCHAR
*
path
)
{
/* Is this path absolute? */
return
path
[
0
]
==
L'\\'
||
path
[
0
]
==
L'/'
||
path
[
1
]
==
L':'
;
}
int
_is_absA
(
char
*
path
)
{
/* Is this path absolute? */
return
path
[
0
]
==
'\\'
||
path
[
0
]
==
'/'
||
path
[
1
]
==
':'
;
}
void
_joinW
(
WCHAR
*
dest_path
,
const
WCHAR
*
root
,
const
WCHAR
*
rest
)
{
/* join root and rest with a backslash */
int
root_len
;
if
(
_is_absW
(
rest
))
{
wcscpy
(
dest_path
,
rest
);
return
;
}
root_len
=
wcslen
(
root
);
wcscpy
(
dest_path
,
root
);
if
(
root_len
)
{
dest_path
[
root_len
]
=
*
L"
\\
"
;
root_len
+=
1
;
}
wcscpy
(
dest_path
+
root_len
,
rest
);
}
void
_joinA
(
char
*
dest_path
,
const
char
*
root
,
const
char
*
rest
)
{
/* join root and rest with a backslash */
int
root_len
;
if
(
_is_absA
(
rest
))
{
strcpy
(
dest_path
,
rest
);
return
;
}
root_len
=
strlen
(
root
);
strcpy
(
dest_path
,
root
);
if
(
root_len
)
{
dest_path
[
root_len
]
=
'\\'
;
root_len
+=
1
;
}
strcpy
(
dest_path
+
root_len
,
rest
);
}
int
_check_dirW
(
WCHAR
*
src
,
WCHAR
*
dest
)
{
/* Return True if the path at src relative to dest is a directory */
WIN32_FILE_ATTRIBUTE_DATA
src_info
;
WCHAR
dest_parent
[
MAX_PATH
];
WCHAR
src_resolved
[
MAX_PATH
]
=
L""
;
/* dest_parent = os.path.dirname(dest) */
wcscpy
(
dest_parent
,
dest
);
_dirnameW
(
dest_parent
);
/* src_resolved = os.path.join(dest_parent, src) */
_joinW
(
src_resolved
,
dest_parent
,
src
);
return
(
GetFileAttributesExW
(
src_resolved
,
GetFileExInfoStandard
,
&
src_info
)
&&
src_info
.
dwFileAttributes
&
FILE_ATTRIBUTE_DIRECTORY
);
}
int
_check_dirA
(
char
*
src
,
char
*
dest
)
{
/* Return True if the path at src relative to dest is a directory */
WIN32_FILE_ATTRIBUTE_DATA
src_info
;
char
dest_parent
[
MAX_PATH
];
char
src_resolved
[
MAX_PATH
]
=
""
;
/* dest_parent = os.path.dirname(dest) */
strcpy
(
dest_parent
,
dest
);
_dirnameW
(
dest_parent
);
/* src_resolved = os.path.join(dest_parent, src) */
_joinW
(
src_resolved
,
dest_parent
,
src
);
return
(
GetFileAttributesExA
(
src_resolved
,
GetFileExInfoStandard
,
&
src_info
)
&&
src_info
.
dwFileAttributes
&
FILE_ATTRIBUTE_DIRECTORY
);
}
#endif
#endif
static
PyObject
*
static
PyObject
*
...
@@ -6793,13 +6911,20 @@ posix_symlink(PyObject *self, PyObject *args, PyObject *kwargs)
...
@@ -6793,13 +6911,20 @@ posix_symlink(PyObject *self, PyObject *args, PyObject *kwargs)
}
}
#ifdef MS_WINDOWS
#ifdef MS_WINDOWS
Py_BEGIN_ALLOW_THREADS
Py_BEGIN_ALLOW_THREADS
if
(
dst
.
wide
)
if
(
dst
.
wide
)
{
/* if src is a directory, ensure target_is_directory==1 */
target_is_directory
|=
_check_dirW
(
src
.
wide
,
dst
.
wide
);
result
=
Py_CreateSymbolicLinkW
(
dst
.
wide
,
src
.
wide
,
result
=
Py_CreateSymbolicLinkW
(
dst
.
wide
,
src
.
wide
,
target_is_directory
);
target_is_directory
);
else
}
else
{
/* if src is a directory, ensure target_is_directory==1 */
target_is_directory
|=
_check_dirA
(
src
.
narrow
,
dst
.
narrow
);
result
=
Py_CreateSymbolicLinkA
(
dst
.
narrow
,
src
.
narrow
,
result
=
Py_CreateSymbolicLinkA
(
dst
.
narrow
,
src
.
narrow
,
target_is_directory
);
target_is_directory
);
}
Py_END_ALLOW_THREADS
Py_END_ALLOW_THREADS
if
(
!
result
)
{
if
(
!
result
)
{
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment