Austin Schuh | 1f9aeb4 | 2015-11-12 23:34:49 -0800 | [diff] [blame] | 1 | def _single_fortran_object_impl(ctx): |
| 2 | toolchain_cflags = (ctx.fragments.cpp.compiler_options([]) + |
| 3 | ctx.fragments.cpp.c_options + |
| 4 | ctx.fragments.cpp.unfiltered_compiler_options([]) + ['-fPIC']) |
| 5 | |
| 6 | cmd = toolchain_cflags + ['-c', ctx.file.src.path, '-o', ctx.outputs.pic_o.path] |
| 7 | filtered_cmd = [] |
| 8 | # Strip out the C/C++ specific flags. |
| 9 | exclude_flags = ['-fcolor-diagnostics', |
| 10 | '-Wswitch-enum', |
| 11 | '-Wpointer-arith', |
| 12 | '-Wcast-qual', |
| 13 | '-Wwrite-strings', |
| 14 | '-Wsign-compare', |
| 15 | '-Wformat=2', |
| 16 | '-Werror', |
| 17 | '-Wno-builtin-macro-redefined', |
| 18 | '-D__has_feature(x)=0'] |
| 19 | |
| 20 | for flag in cmd: |
| 21 | if flag not in exclude_flags: |
| 22 | filtered_cmd.append(flag) |
| 23 | |
| 24 | ctx.action( |
Brian Silverman | b2215d0 | 2015-11-23 19:10:15 -0500 | [diff] [blame^] | 25 | inputs = [ctx.file.src] + ctx.files._cc_toolchain, |
Austin Schuh | 1f9aeb4 | 2015-11-12 23:34:49 -0800 | [diff] [blame] | 26 | outputs = [ctx.outputs.pic_o], |
| 27 | mnemonic = "Fortran", |
| 28 | executable = ctx.fragments.cpp.compiler_executable, |
| 29 | arguments = filtered_cmd, |
| 30 | progress_message = 'Building %s' % ctx.outputs.pic_o.short_path, |
| 31 | ) |
| 32 | |
| 33 | def _define_fortran_output(attrs): |
| 34 | if not attrs.src.name.endswith('.f'): |
| 35 | fail('Fortran files must end in \'.f\'', 'src') |
| 36 | |
| 37 | fortran_file_base = attrs.src.name[:-2] |
| 38 | return { |
| 39 | 'pic_o': fortran_file_base + '.pic.o', |
| 40 | } |
| 41 | |
| 42 | |
| 43 | _single_fortran_object = rule( |
| 44 | implementation = _single_fortran_object_impl, |
| 45 | attrs = { |
| 46 | 'src': attr.label(single_file=True, allow_files=FileType(['.f'])), |
| 47 | 'cc_libs': attr.label_list(providers=['cc']), |
Brian Silverman | b2215d0 | 2015-11-23 19:10:15 -0500 | [diff] [blame^] | 48 | # TODO(Brian): Replace this with something more fine-grained from the |
| 49 | # configuration fragment or something. |
| 50 | '_cc_toolchain': attr.label( |
| 51 | default = Label('//tools/cpp:toolchain'), |
| 52 | ), |
Austin Schuh | 1f9aeb4 | 2015-11-12 23:34:49 -0800 | [diff] [blame] | 53 | }, |
| 54 | outputs = _define_fortran_output, |
| 55 | fragments = [ |
| 56 | 'cpp', |
| 57 | ], |
| 58 | ) |
| 59 | |
| 60 | def fortran_library(name, srcs, deps = [], visibility = None): |
| 61 | """Builds a shared library from a set of fortran files. |
| 62 | |
| 63 | Args: |
| 64 | srcs: list of fortran files ending in .f |
| 65 | deps: cc_library or fortran_library dependencies. |
| 66 | """ |
| 67 | pic_o_files = [] |
| 68 | for src in srcs: |
| 69 | pic_o_file = src[:-2] + '.pic.o' |
Brian Silverman | b2215d0 | 2015-11-23 19:10:15 -0500 | [diff] [blame^] | 70 | _single_fortran_object( |
| 71 | name = name + '_' + pic_o_file, |
| 72 | src = src, |
| 73 | visibility = ['//visibility:private'], |
| 74 | ) |
Austin Schuh | 1f9aeb4 | 2015-11-12 23:34:49 -0800 | [diff] [blame] | 75 | pic_o_files.append(pic_o_file) |
| 76 | |
| 77 | native.cc_library( |
| 78 | name = name, |
| 79 | deps = deps, |
| 80 | srcs = pic_o_files, |
| 81 | linkopts = [ |
| 82 | '-lgfortran', |
| 83 | ], |
| 84 | visibility = visibility, |
| 85 | ) |