Gentoo Websites Logo
Go to: Gentoo Home Documentation Forums Lists Bugs Planet Store Wiki Get Gentoo!
Bug 538788 - dev-util/oprofile-1.0.0 - In function ‘open’, inlined from ‘copy_dumpfile’ at opjitconv.c:219:6: /usr/include/bits/fcntl2.h:50:24: error: call to ‘__open_missing_mode’ declared with attribute error: open with O_CREAT in second argument needs 3 arg
Summary: dev-util/oprofile-1.0.0 - In function ‘open’, inlined from ‘copy_dumpfile’ at...
Status: RESOLVED FIXED
Alias: None
Product: Gentoo Linux
Classification: Unclassified
Component: [OLD] Development (show other bugs)
Hardware: All Linux
: Normal normal (vote)
Assignee: Andrew Savchenko
URL: http://marc.info/?l=oprofile-list&m=1...
Whiteboard:
Keywords: PATCH
Depends on:
Blocks:
 
Reported: 2015-02-04 11:39 UTC by Jeroen Roovers (RETIRED)
Modified: 2015-02-09 07:55 UTC (History)
1 user (show)

See Also:
Package list:
Runtime testing required: ---


Attachments
oprofile-1.0.0-open.patch (oprofile-1.0.0-open.patch,340 bytes, patch)
2015-02-04 11:39 UTC, Jeroen Roovers (RETIRED)
Details | Diff

Note You need to log in before you can comment on or make changes to this bug.
Description Jeroen Roovers (RETIRED) gentoo-dev 2015-02-04 11:39:34 UTC
Created attachment 395510 [details, diff]
oprofile-1.0.0-open.patch

opjitconv/opjitconv.c:219: int fd = open(dumpfile, S_IRUSR);

Seems to confuse flags/mode.

I'm not sure the attached patch is correct, since copy_dumpfile() looks utterly confusing as is.

A test case might look like this:

%< %< %< %< %< %< %< %< %< %< %< %< %< %<
#include <stdio.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>

int main(int argc, char ** argv)
{   
    int fd;
    system("rm -v oprofile_file");
    printf("O_CREAT: %d\nS_IRUSR: %d\n\n", O_CREAT, S_IRUSR);
    fd = open("oprofile_file", O_CREAT, S_IRUSR);
    close(fd);
    system("stat oprofile_file");
    system("rm -v oprofile_file");
    fd = open("oprofile_file", S_IRUSR);
    close(fd);
    system("stat oprofile_file");
    system("rm -v oprofile_file");
    return 0;
}
%< %< %< %< %< %< %< %< %< %< %< %< %< %<

with the output on one HPPA system looking like this:

removed ‘oprofile_file’
O_CREAT: 256
S_IRUSR: 256
  
  File: ‘oprofile_file’
  Size: 0               Blocks: 0          IO Block: 4096   regular empty file
Device: 804h/2052d      Inode: 751292      Links: 1
Access: (0400/-r--------)  Uid: (    0/    root)   Gid: (    0/    root)
Access: 2015-02-04 12:37:04.000000000 +0100
Modify: 2015-02-04 12:37:04.000000000 +0100
Change: 2015-02-04 12:37:04.000000000 +0100
 Birth: -
removed ‘oprofile_file’
  File: ‘oprofile_file’
  Size: 0               Blocks: 0          IO Block: 4096   regular empty file
Device: 804h/2052d      Inode: 751292      Links: 1
Access: (7745/-rwsr-Sr-t)  Uid: (    0/    root)   Gid: (    0/    root)
Access: 2015-02-04 12:37:04.000000000 +0100
Modify: 2015-02-04 12:37:04.000000000 +0100
Change: 2015-02-04 12:37:04.000000000 +0100
 Birth: -
removed ‘oprofile_file’
Comment 1 Jeroen Roovers (RETIRED) gentoo-dev 2015-02-06 10:53:01 UTC
I think this bug is more important than the -Wparentheses bug.

Since this involves temporary file creation, and since the error in the Summary is triggered only with fortification checks enabled, it may not be very hard to construct a case for an exploit.
Comment 2 Andrew Savchenko gentoo-dev 2015-02-06 11:17:49 UTC
I'd like to contact upstream on this issues as well as testing patch, this will take some time. I plan to start in a few days.
Comment 3 Jeroen Roovers (RETIRED) gentoo-dev 2015-02-06 20:32:57 UTC
The issue and the patch are pretty straightforward. The code is calling open(2) with the optional third argument as its second argument.

I caught this because it caused an issue in the C preprocessor on HPPA where incidentally O_CREAT == S_IRUSR and I had extra compiler warnings enabled. See /usr/include/bits/fcntl2.h for the mechanism whereby O_CREAT triggers a check for a third argument and bails out when it isn't present.

It is not an issue for the C preprocessor on x86 and amd64 (and probably others) because there it happens to be the case that S_IRUSR used as an open(2) flag instead of a mode modifier matches O_NOCTTY.

O_CREAT : 64
O_NOCTTY: 256
S_IRUSR: 256

In testing the reduced test case from comment #0 on amd64, I see that it fails to create the file, probably in line with what O_NOCTTY is supposed to do. In that case the output is:

rm: cannot remove ‘oprofile_file’: No such file or directory
O_CREAT: 64
S_IRUSR: 256

  File: ‘oprofile_file’
  Size: 0               Blocks: 0          IO Block: 4096   regular empty file
Device: 803h/2051d      Inode: 1142119     Links: 1
Access: (0400/-r--------)  Uid: (    0/    root)   Gid: (    0/    root)
Access: 2015-02-06 21:18:35.227178044 +0100
Modify: 2015-02-06 21:18:35.227178044 +0100
Change: 2015-02-06 21:18:35.227178044 +0100
 Birth: -
removed ‘oprofile_file’
stat: cannot stat ‘oprofile_file’: No such file or directory
rm: cannot remove ‘oprofile_file’: No such file or directory

The first, correct call to open(2) as used after my patch, creates a file if it doesn't exist. The second call to open(2) succeeds on amd64 but it creates no file.

That means the dumpfile is not created at all on some popular architectures.
The copy_dumpfile() function then proceeds to copy that dumpfile to tmp_dumpfile through a call to system(3) designed to preserve dumpfile's permissions, which the author thinks have just been set to 0400 or (S_IRUSR):

    sprintf(sys_cmd_buffer, "/bin/cp -p %s %s", dumpfile, tmp_dumpfile);

So that should always fail there.
Comment 4 Jeroen Roovers (RETIRED) gentoo-dev 2015-02-06 20:59:32 UTC
Comment on attachment 395510 [details, diff]
oprofile-1.0.0-open.patch

http://sourceforge.net/p/oprofile/oprofile/ci/4598ca73b0a367ca46d4a2843261e20e1896773b/
Comment 5 Jeroen Roovers (RETIRED) gentoo-dev 2015-02-06 21:00:35 UTC
So someone already discovered that on MIPS, with the same error message.
Comment 6 Jeroen Roovers (RETIRED) gentoo-dev 2015-02-09 07:55:33 UTC
Fixed in -r1.