This issue tracker has been migrated to GitHub, and is currently read-only.
For more information, see the GitHub FAQs in the Python's Developer Guide.

classification
Title: Missing platform security integrations
Type: Stage:
Components: Build Versions: Python 3.5
process
Status: open Resolution:
Dependencies: Superseder:
Assigned To: Nosy List: Jeffrey.Walton, ammar2
Priority: normal Keywords:

Created on 2014-03-16 19:37 by Jeffrey.Walton, last changed 2022-04-11 14:58 by admin.

Repositories containing patches
http://hg.python.org/cpython
Messages (3)
msg213749 - (view) Author: Jeffrey Walton (Jeffrey.Walton) * Date: 2014-03-16 19:37
$ hg id
3736bf94535c+ tip

A standard Python build does not take a proactive approach to integrating with platform security measures. Attepting to add the measures results in a failed build.

For example:

export CC=/usr/bin/gcc
export CXX=/usr/bin/g++
export CFLAGS="-fPIC -fstack-protector-all -D_FORTIFY_SOURCE=2"
export CXXFLAGS="-fPIC -fstack-protector-all -D_FORTIFY_SOURCE=2"
export LDFLAGS="-pie -Wl,-z,noexecstack -Wl,-z,noexecheap -Wl,-z,now -Wl,-z,relro"

will configure properly, but will fail to build.

The idea is to build executables with {-fPIE,-pie} and build shared objects with {-fPIC,-shared}. Both executables and shared objects get the remaining platform security integrations like stack protectors and NX stacks/heaps.

In the case an object file is used for both an executable and shared object, it should be compiled with -fPIC (and linking will include -pie or -shared as required). Its OK to use -fPIC in place of -fPIE. See http://gcc.gnu.org/bugzilla/show_bug.cgi?id=52885 for details.

*****

Examining the failed compile:

/usr/bin/gcc -pthread -shared -pie -Wl,-z,noexecstack -Wl,-z,noexecheap -Wl,-z,now -Wl,-z,relro -pie -Wl,-z,noexecstack -Wl,-z,noexecheap -Wl,-z,now -Wl,-z,relro -pie -Wl,-z,noexecstack -Wl,-z,noexecheap -Wl,-z,now -Wl,-z,relro -fPIC -fstack-protector-all -D_FORTIFY_SOURCE=2 build/temp.linux-x86_64-3.4/home/jwalton/Desktop/cpython-checkout/Modules/_struct.o -L/usr/lib/x86_64-linux-gnu -L/usr/local/lib -o build/lib.linux-x86_64-3.4/_struct.cpython-34m.so

So, autotools tried to add both -pie (for executables) and -shared (for shared objects). Fail.

The same problem occurs with _struct.cpython-34m.so, _ctypes_test.cpython-34m.so, array.cpython-34m.so, cmath.cpython-34m.so, math.cpython-34m.so, time.cpython-34m.so, _datetime.cpython-34m.so, _random.cpython-34m.so, _bisect.cpython-34m.so, ...

*****

I know I can omit -pie from CFLAGS and CXXFLAGS:

export CC=/usr/bin/gcc
export CXX=/usr/bin/g++
export CFLAGS="-fPIC -fstack-protector-all -D_FORTIFY_SOURCE=2"
export CXXFLAGS="-fPIC -fstack-protector-all -D_FORTIFY_SOURCE=2"
export LDFLAGS="-Wl,-z,noexecstack -Wl,-z,noexecheap -Wl,-z,now -Wl,-z,relro"

but then I have to manually add -pie to Makefile lines with $BUILDPYTHON (and others, like _testembed and _freeze_importlib):

$(BUILDPYTHON):	Modules/python.o $(LIBRARY) $(LDLIBRARY) $(PY3LIBRARY)
	$(LINKCC) -pie $(PY_LDFLAGS) $(LINKFORSHARED) -o $@ Modules/python.o $(BLDLIBRARY) $(LIBS) $(MODLIBS) $(SYSLIBS) $(LDLAST)
...

*****

Examining an executable produced by the modified Makefil with Tobias Klein's Checksec (http://www.trapkit.de/tools/checksec.html) shows the platform security integrations were successfully applied:

$ checksec.sh --file ./python
RELRO           STACK CANARY      NX            PIE             RPATH      RUNPATH      FILE
Full RELRO      Canary found      NX enabled    PIE enabled     No RPATH   No RUNPATH   ./python

*****

Running `make test` with the security integrations worked as expected, and did not result in any adverse behavior (like an abrupt shutdown).

*****

It would be great if Python tested for features like ASLR for executables, and simply added {-fPIE,-pie} as available. The same is true for the other security offerings (_FORTIFY_SOURCE should be added to Release builds only).
msg213751 - (view) Author: Jeffrey Walton (Jeffrey.Walton) * Date: 2014-03-16 20:05
> $ checksec.sh --file ./python
> RELRO           STACK CANARY      NX            PIE             RPATH      RUNPATH      FILE
> Full RELRO      Canary found      NX enabled    PIE enabled     No RPATH   No RUNPATH   ./python

Here's what a standard Python build looks like (without the platform security integrations):

$ checksec.sh --file ./python
RELRO           STACK CANARY      NX            PIE             RPATH      RUNPATH      FILE
No RELRO        No canary found   NX enabled    No PIE          No RPATH   No RUNPATH   ./python

I believe the NX stack is coming Debian's hardening  for amd64's (https://wiki.debian.org/Hardening).
msg408480 - (view) Author: Ammar Askar (ammar2) * (Python committer) Date: 2021-12-13 20:01
Hi Jeffrey, your second solution where you omit `-pie` is almost there. Instead of modifying the Makefile you can pass `-pie` in `LINKFORSHARED`:


export CFLAGS="-fPIC -fstack-protector-all -D_FORTIFY_SOURCE=2"
export CXXFLAGS="-fPIC -fstack-protector-all -D_FORTIFY_SOURCE=2"
export LDFLAGS="-Wl,-z,noexecstack -Wl,-z,noexecheap -Wl,-z,now -Wl,-z,relro"
export LINKFORSHARED="-pie"

$ checksec ./python
[*] '/home/ammar/workspace/cpython/python'
    Arch:     amd64-64-little
    RELRO:    Full RELRO
    Stack:    Canary found
    NX:       NX enabled
    PIE:      PIE enabled
    FORTIFY:  Enabled
History
Date User Action Args
2022-04-11 14:58:00adminsetgithub: 65148
2021-12-13 20:01:41ammar2setnosy: + ammar2
messages: + msg408480
2014-03-16 20:05:42Jeffrey.Waltonsetmessages: + msg213751
2014-03-16 19:37:03Jeffrey.Waltoncreate