98
1 Assessing the Linux Desktop′s Security Ilja van Sprundel <[email protected]>

Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

  • Upload
    others

  • View
    1

  • Download
    0

Embed Size (px)

Citation preview

Page 1: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

1

Assessing the Linux Desktop′s Security

Ilja van Sprundel <[email protected]>

Page 2: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

Who am I?

• IOActive • Director of Penetration Testing • Pentest • Code review • Break stuff for fun and profit

2

Page 3: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

agenda

• Intro • Observations • Problems • More observations • More problems summary • Solutions ?

3

Page 4: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

What this talk is about

• Local security of linux on the desktop

4

Page 5: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

Intro

• Used to use linux as my main desktop machine • Switched to windows about 7 years ago

• Mainly for work reasons

• Have used linux sporadically since then • However, not as a desktop OS

• Things seem to have changed somewhat

5

Page 6: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

Intro

• Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows

and osx gui • It’s pretty clear they want to matter as a desktop

os • 7-10 years ago, it looked like, well, X • Today, it looks like something my grandmother can use

• Also looked at fedora, opensuse, knoppix • Also took a quick look at osx and opensolaris

(openindiana)

6

Page 7: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

7

A decade ago

Page 8: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

8

Now

Page 9: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

Intro

• Initially had about a week or so of time to play around with this

• Made some interesting observations • Simple command line tools • Some code reading

• Found some clear problems • Maybe a solution or two

9

Page 10: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

What was actually done (observations) • Started off with very simple commands to

enumerate some entrypoints • Wanted to see:

• shared memory (and it’s acl’s) (ipcs) • Udp/tcp/unix sockets exposed locally (netstat –pln) • Look at cron scripts • …

10

Page 11: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

What was actually done (observations) • … • Wanted to see:

• Look for world writable files and directories • find / -perm -0666 -type f • find / -perm -0666 -type d

• Enumerate suid files • find / -perm +2000 -o -perm +4000 -type f

• Enumerate dbus system endpoints • dbus-send --system --type=method_call --print-reply --

dest=org.freedesktop.DBus /org/freedesktop/DBus org.freedesktop.DBus.ListNames

11

Page 12: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

What was actually done (observations) • Expected this to be pretty boring and coming up

almost empty handed • Varying results for various distro’s and operating

systems • There seem to be some systemic issues across all

of them • Is no one doing trivial entrypoint analysis before

shipping ?

12

Page 13: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

Overall finds (problems)

• Without disclosing details (bugs aren’t fixed) • world writeable shared memory • World writable scripts • Really really bloated suid binaries • misconfigurations • Over 60 finds in less than a week

• The goal of this talk isn’t any specific bug

13

Page 14: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

• Dbus • Relatively new attack surface • X/Gnome/KDE specific • Ipc mechanism to pull information about the

system or the current session • Session is probably not that interesting • System could be!

14

Page 15: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

• Dbus • Loads of new attack surface

• Configuration • Design (e.g. repurposing) • Implementation (e.g. buffer overflow)

• There seem to be piles and piles of these installed on default linux distro’s (40-60)

15

Page 16: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

• Dbus system • Configure who can read / write to it

• Under what circumstances (root, console, group, default, …) • Where (what interface, …)

• /etc/dbus-1/* • Xml-alike file that specifies this

16

Page 18: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

18

Page 19: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

• Easy to make config mistakes • Similar to android intent permissions being set in

their AndroidManifest.xml file

19

Page 20: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

• I wanted to look a bit closer at the suids • Asked readelf to give me a list of the library

dependencies (readelf –d) • All those libraries themselves are attack surface as

well • Some have just libc • Others depends on huge blobs of network parsers

(e.g. X).

20

Page 21: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

21

ilja@ilja-VirtualBox:~$ readelf -d /usr/bin/kppp Dynamic section at offset 0x82ec8 contains 33 entries: Tag Type Name/Value 0x00000001 (NEEDED) Shared library: [libkde3support.so.4] 0x00000001 (NEEDED) Shared library: [libQt3Support.so.4] 0x00000001 (NEEDED) Shared library: [libkio.so.5] 0x00000001 (NEEDED) Shared library: [libkdeui.so.5] 0x00000001 (NEEDED) Shared library: [libkdecore.so.5] 0x00000001 (NEEDED) Shared library: [libQtCore.so.4] 0x00000001 (NEEDED) Shared library: [libQtDBus.so.4] 0x00000001 (NEEDED) Shared library: [libQtGui.so.4] 0x00000001 (NEEDED) Shared library: [libstdc++.so.6] 0x00000001 (NEEDED) Shared library: [libc.so.6] …

Page 22: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

22

File: /usr/games/gnomine Dynamic section at offset 0x17ea4 contains 35 entries: Tag Type Name/Value 0x00000001 (NEEDED) Shared library: [libgtk-3.so.0] 0x00000001 (NEEDED) Shared library: [libgdk-3.so.0] 0x00000001 (NEEDED) Shared library: [libpangocairo-1.0.so.0] 0x00000001 (NEEDED) Shared library: [libpango-1.0.so.0] 0x00000001 (NEEDED) Shared library: [librsvg-2.so.2] 0x00000001 (NEEDED) Shared library: [libgio-2.0.so.0] 0x00000001 (NEEDED) Shared library: [libgdk_pixbuf-2.0.so.0] 0x00000001 (NEEDED) Shared library: [libgobject-2.0.so.0] 0x00000001 (NEEDED) Shared library: [libglib-2.0.so.0] 0x00000001 (NEEDED) Shared library: [libcairo.so.2] 0x00000001 (NEEDED) Shared library: [libpthread.so.0] 0x00000001 (NEEDED) Shared library: [libc.so.6] …

Page 23: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

• I spend some time zooming in on those using X • X is a client/server protocol to be used for the gui in

most unices • Including most linux distributions

• It’s networked (can be tcp/ip, ipc, …) • Binary protocol

• suids in question are basically clients • You can make them connect to arbitrary X servers

using the DISPLAY variable • Who says these have to be well behaving X servers ?

23

Page 24: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

X network architecture

24

Page 25: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

• The X client libraries (Xlib) are clear attack surface • Spend about a day looking at the network parsing

code in Xlib • Things are really really bad

• Binary protocol parsers in C. • A lot of them written in the 80’s

• Server data appears to be trusted. Very little validation • > 60 trivial bugs

• It’s clear that code was not written with trust boundaries in mind at all. 25

Page 26: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

26

Status XAllocColorCells( register Display *dpy, Colormap cmap, Bool contig, unsigned long *masks, /* LISTofCARD32 */ /* RETURN */ unsigned int nplanes, /* CARD16 */ unsigned long *pixels, /* LISTofCARD32 */ /* RETURN */ unsigned int ncolors) /* CARD16 */ { ... xAllocColorCellsReply rep; ... status = _XReply(dpy, (xReply *)&rep, 0, xFalse); if (status) { _XRead32 (dpy, (long *) pixels, 4L * (long) (rep.nPixels)); _XRead32 (dpy, (long *) masks, 4L * (long) (rep.nMasks)); } ... }

Page 27: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

27

XTimeCoord *XGetMotionEvents(register Display *dpy, Window w, Time start, Time stop, int *nEvents) /* RETURN */ { xGetMotionEventsReply rep; ... if (!_XReply (dpy, (xReply *)&rep, 0, xFalse)) { … } ... if (! (tc = (XTimeCoord *) Xmalloc( (unsigned) (nbytes = (long) rep.nEvents * sizeof(XTimeCoord))))) { ... } ... for (i = rep.nEvents, tcptr = tc; i > 0; i--, tcptr++) { _XRead (dpy, (char *) &xtc, nbytes); tcptr->time = xtc.time; … } ...}

Page 28: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

28

_XkbReadGetDeviceInfoReply( Display * dpy, xkbGetDeviceInfoReply * rep, XkbDeviceInfoPtr devi) { ... if (rep->nBtnsWanted>0) { act= &devi->btn_acts[rep->firstBtnWanted]; bzero((char *)act,(rep->nBtnsWanted*sizeof(XkbAction))); } ... int size; act= &devi->btn_acts[rep->firstBtnRtrn]; size= rep->nBtnsRtrn*SIZEOF(xkbActionWireDesc); if (!_XkbCopyFromReadBuffer(&buf,(char *)act,size)) goto BAILOUT; ... }

Page 29: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

29

Private Bool _XimXGetReadData( Xim im, char *buf, int buf_len, int *ret_len, XEvent *event) { ... return_code = XGetWindowProperty(im->core.display, spec->lib_connect_wid, prop, 0L, (long)((length + 3)/ 4), True, AnyPropertyType, &type_ret, &format_ret, &nitems, &bytes_after_ret, &prop_ret); ... if (buf_len >= length) { (void)memcpy(buf, prop_ret, (int)nitems); ... } ... }

Page 30: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

30

static char * ReadInFile(_Xconst char *filename) { register int fd, size; ... if ( (fd = _XOpenFile (filename, O_RDONLY)) == -1 ) return (char *)NULL; ... if ( (fstat(fd, &status_buffer)) == -1 ) { close (fd); return (char *)NULL; } else size = status_buffer.st_size; } if (!(filebuf = Xmalloc(size + 1))) { /* leave room for '\0' */ close(fd); return (char *)NULL; } size = read (fd, filebuf, size); ... }

Page 31: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

31

static char* TransFileName(Xim im, char *name) { char *home = NULL, *lcCompose = NULL; char dir[XLC_BUFSIZE]; char *i = name, *ret, *j; int l = 0; while (*i) { if (*i == '%') { i++; switch (*i) { case 'H': home = getenv("HOME"); if (home) l += strlen(home); possible int overflow (long HOME and loads of %H's) break; case 'L': if (lcCompose == NULL) lcCompose = _XlcFileName(im->core.lcd, COMPOSE_FILE); if (lcCompose) l += strlen(lcCompose); possible integer overflow (long lcCompose and loads of %L's) break; case 'S': xlocaledir(dir, XLC_BUFSIZE); l += strlen(dir); possible integer overflow (long dir and loads of %S's) break;

Page 32: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations (cont)

32

j = ret = Xmalloc(l+1); integer overflow, alloc too short if any of the int overflows occured ... i = name; while (*i) { if (*i == '%') { i++; switch (*i) { case '%': *j++ = '%'; break; case 'H': if (home) { strcpy(j, home); buffer overflow if integer overflow occured j += strlen(home); } break; case 'L': if (lcCompose) { strcpy(j, lcCompose); buffer overflow if integer overflow occured j += strlen(lcCompose); } break; case 'S': strcpy(j, dir); buffer overflow if integer overflow occured j += strlen(dir); break;

Page 33: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

33

XFixesCursorImage *XFixesGetCursorImage (Display *dpy) { ... xXFixesGetCursorImageAndNameReply rep; int npixels; ... if (!_XReply (dpy, (xReply *) &rep, 0, xFalse)) { ... } ... npixels = rep.width * rep.height; ushort * ushort ... rlength = (sizeof (XFixesCursorImage) + npixels * sizeof (unsigned long) + nbytes_name + 1); ... image = (XFixesCursorImage *) Xmalloc (rlength); ... image->x = rep.x; ... }

Page 34: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

34

Bool DMXGetScreenAttributes(Display *dpy, int physical_screen, DMXScreenAttributes *attr) { ... xDMXGetScreenAttributesReply rep; ... if (!_XReply(dpy, (xReply *)&rep, (SIZEOF(xDMXGetScreenAttributesReply) - 32) >> 2, xFalse)) { UnlockDisplay(dpy); SyncHandle(); return False; } attr->displayName = Xmalloc(rep.displayNameLength + 1 + 4 /* for pad */); _XReadPad(dpy, attr->displayName, rep.displayNameLength); attr->displayName[rep.displayNameLength] = '\0'; ... }

Page 35: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

35

int XGetDeviceButtonMapping( register Display *dpy, XDevice *device, unsigned char map[], unsigned int nmap) { int status = 0; unsigned char mapping[256]; /* known fixed size */ ... xGetDeviceButtonMappingReply rep; ... status = _XReply(dpy, (xReply *) & rep, 0, xFalse); if (status == 1) { nbytes = (long)rep.length << 2; _XRead(dpy, (char *)mapping, nbytes); ... } ... }

Page 36: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

36

XEventClass * XGetDeviceDontPropagateList( register Display *dpy, Window window, int *count) { ... xGetDeviceDontPropagateListReply rep; ... if (!_XReply(dpy, (xReply *) & rep, 0, xFalse)) { ... } ... list = (XEventClass *) Xmalloc(rep.length * sizeof(XEventClass)); if (list) { ... for (i = 0; i < rep.length; i++) { _XRead(dpy, (char *)(&ec), sizeof(CARD32)); list[i] = (XEventClass) ec; } }

Page 37: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

37

static int _XIPassiveGrabDevice(Display* dpy, int deviceid, int grabtype, int detail, Window grab_window, Cursor cursor, int grab_mode, int paired_device_mode, Bool owner_events, XIEventMask *mask, int num_modifiers, XIGrabModifiers *modifiers_inout) { ... if (!_XReply(dpy, (xReply *)&reply, 0, xFalse)) { ... } failed_mods = calloc(reply.num_modifiers, sizeof(xXIGrabModifierInfo)); ... _XRead(dpy, (char*)failed_mods, reply.num_modifiers * sizeof(xXIGrabModifierInfo)); for (i = 0; i < reply.num_modifiers; i++) { modifiers_inout[i].status = failed_mods[i].status; … }

Page 38: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

38

XineramaScreenInfo * XineramaQueryScreens( Display *dpy, int *number ) { XExtDisplayInfo *info = find_display (dpy); xXineramaQueryScreensReply rep; .... if((scrnInfo = Xmalloc(sizeof(XineramaScreenInfo) * rep.number))) { ... for(i = 0; i < rep.number; i++) { _XRead(dpy, (char*)(&scratch), sz_XineramaScreenInfo); scrnInfo[i].screen_number = i; scrnInfo[i].x_org = scratch.x_org; scrnInfo[i].y_org = scratch.y_org; scrnInfo[i].width = scratch.width; scrnInfo[i].height = scratch.height; } ... }

Page 39: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

39

XvImageFormatValues * XvListImageFormats ( Display *dpy, XvPortID port, int *num ){ ... xvListImageFormatsReply rep; ... if (_XReply(dpy, (xReply *)&rep, 0, xFalse) == 0) { ... } ... int size = (rep.num_formats * sizeof(XvImageFormatValues)); ... if((ret = Xmalloc(size))) { ... for(i = 0; i < rep.num_formats; i++) { ... } } ...

Page 40: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

40

Bool XF86VidModeGetGammaRamp ( Display *dpy, int screen, int size, unsigned short *red, unsigned short *green, unsigned short *blue ) { ... xXF86VidModeGetGammaRampReply rep; ... if (!_XReply (dpy, (xReply *) &rep, 0, xFalse)) { ... } if(rep.size) { _XRead(dpy, (char*)red, rep.size << 1); _XRead(dpy, (char*)green, rep.size << 1); _XRead(dpy, (char*)blue, rep.size << 1); } ... }

Page 41: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

41

Bool uniDRIOpenConnection(dpy, screen, hSAREA, busIdString) Display *dpy; int screen; drm_handle_t *hSAREA; char **busIdString; { ... xXF86DRIOpenConnectionReply rep; ... if (!(*busIdString = (char *)Xcalloc(rep.busIdStringLength + 1, 1))) { ... } _XReadPad(dpy, *busIdString, rep.busIdStringLength); ... }

Page 42: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

42

static XcursorFileHeader * _XcursorReadFileHeader (XcursorFile *file) { ... if (!_XcursorReadUInt (file, &head.ntoc)) unsigned 32bit ntoc var read from file return NULL; ... fileHeader = _XcursorFileHeaderCreate (head.ntoc); passed on to allocate buffer ... for (n = 0; n < fileHeader->ntoc; n++) { if (!_XcursorReadUInt (file, &fileHeader->tocs[n].type)) break; if (!_XcursorReadUInt (file, &fileHeader->tocs[n].subtype)) break; if (!_XcursorReadUInt (file, &fileHeader->tocs[n].position)) break; } ... }

Page 43: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations (cont)

43

static XcursorFileHeader * _XcursorFileHeaderCreate (int ntoc) { XcursorFileHeader *fileHeader; if (ntoc > 0x10000) return NULL; fileHeader = malloc (sizeof (XcursorFileHeader) + ntoc * sizeof (XcursorFileToc)); if (!fileHeader) return NULL; fileHeader->magic = XCURSOR_MAGIC; fileHeader->header = XCURSOR_FILE_HEADER_LEN; fileHeader->version = XCURSOR_FILE_VERSION; fileHeader->ntoc = ntoc; fileHeader->tocs = (XcursorFileToc *) (fileHeader + 1); return fileHeader; }

Page 44: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

44

static void ReqCleanup( Widget widget, XtPointer closure, XEvent *ev, Boolean *cont) { ... char *value; ... (void) XGetWindowProperty(event->display, XtWindow(widget), event->atom, 0L, 1000000, True, AnyPropertyType, &target, &format, &length, &bytesafter, (unsigned char **) &value); should check return value. XFree(value); ... }

Page 45: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

• The X client libraries (Xlib) • All discovered X bugs are being fixed • The developer involved is actually quite good

• Amazing • Alan Coopersmith • Very deep understanding of X and the bugs involved • No pushback, no handholding • Worked tirelessly • 104 patches, with reviews and some tests in < 3 months

• And had some interesting comments

45

Page 46: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

46

“I don't know how many setuid X clients still exist these days (is xterm still setuid on any platforms, or did they all get grantpt() or similar calls to avoid needing root?), but since we know there's more X clients than we can keep track of (especially once you get to home grown apps in various companies

they've been using for decades), we have to assume there still may be some. It would be good to put a reminder in the security advisory that best practice is to separate out the parts of an application that require elevated privileges from the

GUI to avoid such issues - GTK requires this, but not all toolkits do.”

More observations

Page 47: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

47

“Shoot me now. And then shoot daniels for not freeing us from XKB yet. And then shoot anyone who volunteers to try to fix XKB, before it's too late for them too.”

“Here's my initial analysis of the first part of the Xlib set, until I got so tired my head started spinning trying to figure them out”

“Really, if your window shape is anywhere near 2^32 rectangles, what are you doing?”

“Yes, these [bugs] all seem possible, and far more feasible now than when this code was written, back when disk sizes were still measured in megabytes.”

Page 48: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

• Comment on LWN from one of the people that introduced some of these bugs in the ‘80’s

48

Page 49: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

• Debian’s turn around on these bugs was ridiculously fast!

• 104 patches to merge in • 2 week embargo • Full releases and advisory on day embargo expired

• No one else managed to do this

• I think Moritz Mühlenhoff deserves most of the credit for that one

49

Page 50: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

• However, Raw X is rarely used nowadays • There’s stuff build on top • And they use raw X

• gtk+ • KDE (which uses QT which uses raw X) • Rare direct calls to Xlib code • other

50

Page 51: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

• KDE / QT • Crappyness is about on par with Xlib • Trivial bugs!

51

Page 52: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

• Several instances of this

52

Qkeymapper_x11.cpp void QKeyMapperPrivate::clearMappings() { ... uchar *data = 0; if (XGetWindowProperty(X11->display, RootWindow(X11->display, 0), ATOM(_XKB_RULES_NAMES), 0, 1024, false, XA_STRING, &type, &format, &nitems, &bytesAfter, &data) == Success && type == XA_STRING && format == 8 && nitems > 2) { ... char *names[5] = { 0, 0, 0, 0, 0 }; char *p = reinterpret_cast<char *>(data), *end = p + nitems; int i = 0; do { names[i++] = p; p += qstrlen(p) + 1; } while (p < end); ... }

Page 53: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

• In QT init code (affects all QT applications)

53

Qapplication_x11.cpp void qt_init(QApplicationPrivate *priv, int, Display *display, Qt::HANDLE visual, Qt::HANDLE colormap) { ... } else if (arg == "-name") { if (++i < argc) appName = argv[i]; if it was previously new'ed, it isn't anymore. } ... } void qt_cleanup() { ... if (X11->foreignDisplay) { delete [] (char *)appName; could delete [] a pointer that isn't new'ed and possibly corrupt memory appName = 0; } ... }

Page 54: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

• So I reported these bugs • They didn’t seem to think it was a security issues • Quote from X developer (previous slide) is dead on

• Suid remark

• QT does not seem to agree with this

54

Page 55: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

• "KDE has precisely one setuid application, kcheckpass, for this reason. I suspect that someone running an suid Qt application would fall into a huge number of problems, the most obvious one being a malicious style that would allow them to trivially execute arbitrary code“

• Wait, did we just get a free Code exec bug from the QT security team ?

55

Page 56: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

• I respond back, saying there are more KDE suid binaries, and specifically mention kppp, and question him on the styles thing

56

Page 57: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

57

“> I am aware of this, regardless, this is library code, as such, chances are, there are suid applications out there that will use it. That would be a security hole in those applications rather than in Qt, there are many ways that people can abuse a library to create unsafe applications. > Do styles contain executable code ? Yes.”

Page 58: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

58

“> also, does kppp no longer run suid ? kppp should not be installed setuid. Here's a quote from its FAQ: "There is no need for the setuid bit, if you know a bit of UNIX® systems administration. Simply create a modem group, add all users that you want to give access to the modem to that group and make the modem device read/writable for that group." I doubt any modern distro would install it suid, in fact most are extremely careful about what they allow to be suid and are actively working to minimise what is.”

More observations

Page 59: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

• That kppp FAQ quote in incomplete, it goes on to say:

59

“… The KPPP team has lately done a lot of work to make KPPP setuid-safe. But it's up to you to decide if you install and how you install it.”

Page 60: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

• In fact, distro’s do still have it suid. • E.g. Ubuntu • This is library code! They should not set policy for

the apps that use them. • They’re sitting on the fence, because it’s easy

• you don’t actually have to do anything

• Either defend it, and shut up • Or do a suid check and exit()

60

Page 61: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

• None of those bugs are fixed • Got the ok from QT security team to disclose:

61

“> Ok, since you guys don't consider this a security issue, you're ok with me talking about this publicly? Yes, that's fine”

Page 62: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

• So loaders have LD_PRELOAD • And has been made setuid safe years ago • KDE/QT

• QT_PLUGIN_PATH

• Gnome • GTK_MODULES

• Neither are setuid safe !

62

Page 63: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

• The GTK+ people seem to be doing somewhat better.

• They do not allow suid GTK+ applications. • And clearly explain why on their webpage

63

Page 64: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations (http://www.gtk.org/setuid.html)

Talking Radios born from taco trucks

64

Page 65: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

• This is beautiful, well though out and sane! • “Security of GTK+ requires the security of Xlib. The

GTK+ team is not prepared to make that guarantee”

• Or is it ?

65

Page 66: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

66

Gtkmain.c /* This checks to see if the process is running suid or sgid * at the current time. If so, we don't allow GTK+ to be initialized. * This is meant to be a mild check - we only error out if we * can prove the programmer is doing something wrong, not if * they could be doing something wrong. For this reason, we * don't use issetugid() on BSD or prctl (PR_GET_DUMPABLE). */ static gboolean check_setugid (void)

Page 67: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

• What does that mean ? • Suid binaries can use GTK+, BUT … • … they must acquire the privileged resources they

want first • And then drop privileges • After that it’s ok to use GTK+ • Want to have their cake and eat it too • Check should be stronger!

67

Page 68: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

• games are a great example • They are suid

• Share a highscore database

• Once aquired, privs are dropped • Only thing an attacker would have access to is that db

• assuming a bug was found and exploited

• That db is considered trusted. • Any security bug in db parsing allows for further escalation

• Any user now playing any of those games gets pwned 68

Page 69: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

• Spend a little bit of time looking at x display managers • There’s a lot of them • Uses xdmcp protocol (goes over udp) • Most have dependency on libxdmcp for this • Libxdmcp’s api’s quite easily lend themselves to

abuse • Leaves a lot of stuff uninitialized on failure

• This is being fixed

69

Page 70: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

• LightDM • Used by ubuntu

• Has so called greeters that allow you to customize the gui

• Unpriv’ed greeters talk to LightDM • Using a pipe

• Parser for that pipe wasn’t great • Not that bad either

• Bugs are being fixed 70

Page 71: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

71

static gboolean read_cb (GIOChannel *source, GIOCondition condition, gpointer data) { Greeter *greeter = data; gsize n_to_read, n_read, offset; ... n_to_read = HEADER_SIZE; if (greeter->priv->n_read >= HEADER_SIZE) { offset = int_length (); n_to_read += read_int (greeter, &offset); [2] } status = g_io_channel_read_chars (greeter->priv->from_greeter_channel, (gchar *) greeter->priv->read_buffer + greeter->priv->n_read, n_to_read - greeter->priv->n_read, [3] &n_read, &error); ... greeter->priv->n_read += n_read; if (greeter->priv->n_read != n_to_read) return TRUE; /* If have header, rerun for content */ if (greeter->priv->n_read == HEADER_SIZE) { gsize offset = int_length (); n_to_read = read_int (greeter, &offset); if (n_to_read > 0) { greeter->priv->read_buffer = secure_realloc (greeter, greeter->priv->read_buffer, HEADER_SIZE + n_to_read); [1] read_cb (source, condition, greeter); return TRUE; } } ... }

Page 72: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

1. integer overflow when allocating buffer 2. Integer overflow (really small n_to_read) 3. Integer underflow, size to read becomes really large

72

Page 73: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

• As mentioned earlier, libraries build on top of X use Xlib

• Apps will sometimes also call some X api’s to query certain things

• Using the XGetWindowProperty() api or any number of api’s build on top of it (e.g. XGetClassHint(), XGetRGBColormaps(), …)

• Looked at the use of Xlib api’s • This too wasn’t great

73

Page 74: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

• By far the most common bug when using Xlib

• Check return values ! • XLib defense in depth fixes. Now guarantees NULL

init of arguments on failure. 74

void fn() { ... SomeFormat *sf; ... (void) XGetWindowProperty(dpy, w, property, 0L, 10000000, False, SomePropertyType, &type, &format, &length, &bytesafter, (unsigned char **) &sf); ... XFree((char*)sf); ... }

Page 75: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

• Developers using Xlib don’t seem to realize that most of the api’s they use parse potentially untrusted network data

• _XReply

• _XRead32

• _XRead

• _XGetAsyncReply

• XGetWindowProperty

• XNextEvent

• XPeekEventXIfEvent

• XCheckIfEvent

• XPeekIfEvent

• XCheckTypedWindowEvent

• XSetErrorHandler

• XQueryFont

75

Page 76: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

• derived from XGetWindowProperty: • XFetchName

• XGetIconName

• XGetSizeHints

• XGetWMHints

• XGetWMSizeHints

• XGetIconSizes

• XGetTransientForHint

• XGetClassHint

• XGetRGBColormaps

• XGetTextProperty

• XGetWMName

• XGetWMIconName

• XGetWMClientMachine

• XGetCommand

• XGetWMColormapWindows

• XGetWMProtocols 76

• XScreenResourceString • XFetchBuffer • XFetchBytes • XkbRF_GetNamesProp

Page 77: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

• Conceptually there’s a couple of X suid apps around that you’ll see:

• Config tools (e.g. kppp) • Games (e.g. swell foop) • Screen locking utils (e.g. Xlock, Xlockmore, Xscreensaver, …)

• Virtually all of these apps do drop privileges

77

Page 78: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

• the screenlocking utils • Only seem to capture your hashed pw entry (and

optionally root). • Getspnam()

• W00t. That’s not much of a resource • Or is it ?

78

Page 79: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More observations

• The linux shadow library is responsible for api’s for reading from and writing to the shadow file

• Shadow.h • The code uses FILE stream api’s to read and write

• Uses heap buffers internally, Can’t clear memory.

• Stores read data in local stack buffers • Doesn’t clear memory

• Basically leaks the entire shadow file onto the heap and the stack

79

Page 80: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

More problems summary

• Xlib in suids is a bad idea • GTK+ kinda sorta still allowed in suids • Very common sloppy misuse of Xlib api’s • Linux shadow library handles sensitive data in a

sloppy manner

80

Page 81: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

todo

• There’s some other things we wanted to look at but didn’t get around too

• Package managers • Clipboard

• Ok, we did look for about 5 seconds • It did look bad …. 81

Page 82: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

todo

• Fedora package management (software)

82

Page 83: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

todo

• Ubuntu apt-get

83

Page 84: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

todo

• OpenSuse zypper

84

Page 85: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

todo

• Lets hope they sign stuff • And check it

• And have signatures locally • Or fetch them securely from a remote host

• And don’t use md5 … • Even if you’ve got all this correct • Network protocol is unencrypted • Adds a lot of remote attack surface

85

Page 86: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

todo

• Clipboard • ICCCM • It smells rotten • http://lists.slug.org.au/archives/slug-

chat/2001/July/msg00054.html • Srsly, go read it • No, really! • It’s all I know about ICCCM, but it speaks volumes

86

Page 87: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

todo

87

“d00d, that document is devilspawn…. what sick evil twisted mind wrote this damn spec?”

“The ICCCM is the coding equivalent of the Medieval rack, except its advertised as some kind of X11 swingers party.”

“I've seen more elegant protocols in unlikely places. When blowflies fight over a pile of elephant shit, their pecking order is a more elegant protocol than ICCCM.”

“I. C. C. C. M. Inter- Client Communications Conventions Manual! Manual, like in "manual labour", like in "pain" Conventions, like in "not required, just do ALL OF IT or you SUCK!" Communications, like in "fucking overengineered carrier pigeons" Client, like in "see that guy with the limp, he was one of my ``clients''" Inter-, like in "Inter-nal bleeding“”

Page 88: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

Solutions ?

• The shadow library thing is easy to fix • It’s not really a bug in the first place

• But exposes too much sensitive information to an already compromised suid program

• Drop all FILE stream usage. • Use open/read/write syscalls instead

• Clear all memory after use • Make sure memset() doesn’t get optimized out by compiler

88

Page 89: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

Solutions ?

• Most suids on linux (and most unices) have been dropping privileges for a long time

• Nothing has changed since

• This isn’t good enough. • Those privileged resources include:

• read fd to /dev/kmem • read/write fd to /etc/resolv.conf • Full content of /etc/shadow • …

89

Page 90: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

Solutions ?

• The suid processes still have their suid bit set in kernel • Attacker still needs some kind of bug + exploit • reduced what can be gained from uid 0 to those

resources • Is however still very significant

90

Page 91: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

Solutions ?

• A model where priv dropping and priv separation is combined would make more sense

• Would add more defense in depth • Probably not that hard to implement for some suids

91

Page 92: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

Solutions ?

• Here’s what it would looks like: • pipe • fork • client drops all privs • server gets resources • server drops privs • very small and well defined interface between client and

server

92

Page 93: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

Solutions ?

• Client retains it’s suid bit • Pipe to server is protected from injection

• readelf –d on some of the suids • HUGE list of library dependencies!

• We don’t want that in service code. • fork() is out!

• If you fork, all that stuff is still in memory.

93

Page 94: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

Solutions ?

• fork() is out, fork() + execve() is in. • Pass fd to excve’ed process. • Server has to be a very small piece of c code. • Only access to libc.

94

Page 95: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

Solutions ?

• Actually, glibc (default on most distributions) is super bloated.

• > 100mb of source code (2.1.7) • memfrob() ? • strfry() ???

• Can you really trust that ? • Should not be used in server app • Instead use something like dietlibc, uClibc, klibc or

musl

95

Page 96: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

Solutions ?

• One last piece of code bloat left • Dynamic loader. • Takes input though environment variables • Have been bugs in there in the past • Do you really want to trust it ? • Fix: static binaries

96

Page 97: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

Conclusion?

• Guess there should be a conclusion • Run for the hills ? • Things could be better … • … by several orders of magnitude

• There’s really a lot of work to be done here

• most of that code is not written with a trust boundary in mind

97

Page 98: Assessing the Linux Desktop′s · 2018. 11. 10. · Intro • Installed ubuntu during the holidays last year • Boots into a gui, looks like some mix of windows and osx gui •

98

Questions ?