Home | History | Annotate | Download | only in make
      1 #!/bin/bash
      2 ##
      3 ##  Copyright (c) 2010 The WebM project authors. All Rights Reserved.
      4 ##
      5 ##  Use of this source code is governed by a BSD-style license
      6 ##  that can be found in the LICENSE file in the root of the source
      7 ##  tree. An additional intellectual property rights grant can be found
      8 ##  in the file PATENTS.  All contributing project authors may
      9 ##  be found in the AUTHORS file in the root of the source tree.
     10 ##
     11 
     12 
     13 self=$0
     14 self_basename=${self##*/}
     15 EOL=$'\n'
     16 EOLDOS=$'\r'
     17 
     18 show_help() {
     19     cat <<EOF
     20 Usage: ${self_basename} [options] file1 [file2 ...]
     21 
     22 This script generates a Visual Studio 2005 solution file from a list of project
     23 files.
     24 
     25 Options:
     26     --help                      Print this message
     27     --out=outfile               Redirect output to a file
     28     --ver=version               Version (7,8,9,10,11) of visual studio to generate for
     29     --target=isa-os-cc          Target specifier
     30 EOF
     31     exit 1
     32 }
     33 
     34 die() {
     35     echo "${self_basename}: $@" >&2
     36     [ -f "${outfile}" ] && rm -f ${outfile}{,.mk}
     37     exit 1
     38 }
     39 
     40 die_unknown(){
     41     echo "Unknown option \"$1\"." >&2
     42     echo "See ${self_basename} --help for available options." >&2
     43     [ -f "${outfile}" ] && rm -f ${outfile}{,.mk}
     44     exit 1
     45 }
     46 
     47 indent1=$'\t'
     48 indent=""
     49 indent_push() {
     50     indent="${indent}${indent1}"
     51 }
     52 indent_pop() {
     53     indent="${indent%${indent1}}"
     54 }
     55 
     56 parse_project() {
     57     local file=$1
     58     if [ "$sfx" = "vcproj" ]; then
     59         local name=`grep Name "$file" | awk 'BEGIN {FS="\""}{if (NR==1) print $2}'`
     60         local guid=`grep ProjectGUID "$file" | awk 'BEGIN {FS="\""}{if (NR==1) print $2}'`
     61     else
     62         local name=`grep RootNamespace "$file" | sed 's,.*<.*>\(.*\)</.*>.*,\1,'`
     63         local guid=`grep ProjectGuid "$file" | sed 's,.*<.*>\(.*\)</.*>.*,\1,'`
     64     fi
     65 
     66     # save the project GUID to a varaible, normalizing to the basename of the
     67     # vcproj file without the extension
     68     local var
     69     var=${file##*/}
     70     var=${var%%.${sfx}}
     71     eval "${var}_file=\"$1\""
     72     eval "${var}_name=$name"
     73     eval "${var}_guid=$guid"
     74 
     75     if [ "$sfx" = "vcproj" ]; then
     76         cur_config_list=`grep -A1 '<Configuration' $file |
     77             grep Name | cut -d\" -f2`
     78     else
     79         cur_config_list=`grep -B1 'Label="Configuration"' $file |
     80             grep Condition | cut -d\' -f4`
     81     fi
     82     new_config_list=$(for i in $config_list $cur_config_list; do
     83         echo $i
     84     done | sort | uniq)
     85     if [ "$config_list" != "" ] && [ "$config_list" != "$new_config_list" ]; then
     86         mixed_platforms=1
     87     fi
     88     config_list="$new_config_list"
     89     eval "${var}_config_list=\"$cur_config_list\""
     90     proj_list="${proj_list} ${var}"
     91 }
     92 
     93 process_project() {
     94     eval "local file=\${$1_file}"
     95     eval "local name=\${$1_name}"
     96     eval "local guid=\${$1_guid}"
     97 
     98     # save the project GUID to a varaible, normalizing to the basename of the
     99     # vcproj file without the extension
    100     local var
    101     var=${file##*/}
    102     var=${var%%.${sfx}}
    103     eval "${var}_guid=$guid"
    104 
    105     echo "Project(\"{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}\") = \"$name\", \"$file\", \"$guid\""
    106     indent_push
    107 
    108     eval "local deps=\"\${${var}_deps}\""
    109     if [ -n "$deps" ] && [ "$sfx" = "vcproj" ]; then
    110         echo "${indent}ProjectSection(ProjectDependencies) = postProject"
    111         indent_push
    112 
    113         for dep in $deps; do
    114             eval "local dep_guid=\${${dep}_guid}"
    115             [ -z "${dep_guid}" ] && die "Unknown GUID for $dep (dependency of $var)"
    116             echo "${indent}$dep_guid = $dep_guid"
    117         done
    118 
    119         indent_pop
    120         echo "${indent}EndProjectSection"
    121 
    122     fi
    123 
    124     indent_pop
    125     echo "EndProject"
    126 }
    127 
    128 process_global() {
    129     echo "Global"
    130     indent_push
    131 
    132     #
    133     # Solution Configuration Platforms
    134     #
    135     echo "${indent}GlobalSection(SolutionConfigurationPlatforms) = preSolution"
    136     indent_push
    137     IFS_bak=${IFS}
    138     IFS=$'\r'$'\n'
    139     if [ "$mixed_platforms" != "" ]; then
    140         config_list="
    141 Release|Mixed Platforms
    142 Debug|Mixed Platforms"
    143     fi
    144     for config in ${config_list}; do
    145         echo "${indent}$config = $config"
    146     done
    147     IFS=${IFS_bak}
    148     indent_pop
    149     echo "${indent}EndGlobalSection"
    150 
    151     #
    152     # Project Configuration Platforms
    153     #
    154     echo "${indent}GlobalSection(ProjectConfigurationPlatforms) = postSolution"
    155     indent_push
    156     for proj in ${proj_list}; do
    157         eval "local proj_guid=\${${proj}_guid}"
    158         eval "local proj_config_list=\${${proj}_config_list}"
    159         IFS=$'\r'$'\n'
    160         for config in ${proj_config_list}; do
    161             if [ "$mixed_platforms" != "" ]; then
    162                 local c=${config%%|*}
    163                 echo "${indent}${proj_guid}.${c}|Mixed Platforms.ActiveCfg = ${config}"
    164                 echo "${indent}${proj_guid}.${c}|Mixed Platforms.Build.0 = ${config}"
    165             else
    166                 echo "${indent}${proj_guid}.${config}.ActiveCfg = ${config}"
    167                 echo "${indent}${proj_guid}.${config}.Build.0 = ${config}"
    168             fi
    169 
    170         done
    171         IFS=${IFS_bak}
    172     done
    173     indent_pop
    174     echo "${indent}EndGlobalSection"
    175 
    176     #
    177     # Solution Properties
    178     #
    179     echo "${indent}GlobalSection(SolutionProperties) = preSolution"
    180     indent_push
    181     echo "${indent}HideSolutionNode = FALSE"
    182     indent_pop
    183     echo "${indent}EndGlobalSection"
    184 
    185     indent_pop
    186     echo "EndGlobal"
    187 }
    188 
    189 process_makefile() {
    190     IFS_bak=${IFS}
    191     IFS=$'\r'$'\n'
    192     local TAB=$'\t'
    193     cat <<EOF
    194 ifeq (\$(CONFIG_VS_VERSION),7)
    195 MSBUILD_TOOL := devenv.com
    196 else
    197 MSBUILD_TOOL := msbuild.exe
    198 endif
    199 found_devenv := \$(shell which \$(MSBUILD_TOOL) >/dev/null 2>&1 && echo yes)
    200 .nodevenv.once:
    201 ${TAB}@echo "  * \$(MSBUILD_TOOL) not found in path."
    202 ${TAB}@echo "  * "
    203 ${TAB}@echo "  * You will have to build all configurations manually using the"
    204 ${TAB}@echo "  * Visual Studio IDE. To allow make to build them automatically,"
    205 ${TAB}@echo "  * add the Common7/IDE directory of your Visual Studio"
    206 ${TAB}@echo "  * installation to your path, eg:"
    207 ${TAB}@echo "  *   C:\Program Files\Microsoft Visual Studio 8\Common7\IDE"
    208 ${TAB}@echo "  * "
    209 ${TAB}@touch \$@
    210 CLEAN-OBJS += \$(if \$(found_devenv),,.nodevenv.once)
    211 
    212 EOF
    213 
    214     for sln_config in ${config_list}; do
    215         local config=${sln_config%%|*}
    216         local platform=${sln_config##*|}
    217         local nows_sln_config=`echo $sln_config | sed -e 's/[^a-zA-Z0-9]/_/g'`
    218         cat <<EOF
    219 BUILD_TARGETS += \$(if \$(NO_LAUNCH_DEVENV),,$nows_sln_config)
    220 clean::
    221 ${TAB}rm -rf "$platform"/"$config"
    222 .PHONY: $nows_sln_config
    223 ifneq (\$(found_devenv),)
    224   ifeq (\$(CONFIG_VS_VERSION),7)
    225 $nows_sln_config: $outfile
    226 ${TAB}\$(MSBUILD_TOOL) $outfile -build "$config"
    227 
    228   else
    229 $nows_sln_config: $outfile
    230 ${TAB}\$(MSBUILD_TOOL) $outfile -m -t:Build \\
    231 ${TAB}${TAB}-p:Configuration="$config" -p:Platform="$platform"
    232 
    233   endif
    234 else
    235 $nows_sln_config: $outfile .nodevenv.once
    236 ${TAB}@echo "  * Skipping build of $sln_config (\$(MSBUILD_TOOL) not in path)."
    237 ${TAB}@echo "  * "
    238 endif
    239 
    240 EOF
    241     done
    242     IFS=${IFS_bak}
    243 }
    244 
    245 # Process command line
    246 outfile=/dev/stdout
    247 for opt in "$@"; do
    248     optval="${opt#*=}"
    249     case "$opt" in
    250     --help|-h) show_help
    251     ;;
    252     --out=*) outfile="${optval}"; mkoutfile="${optval}".mk
    253     ;;
    254     --dep=*) eval "${optval%%:*}_deps=\"\${${optval%%:*}_deps} ${optval##*:}\""
    255     ;;
    256     --ver=*) vs_ver="$optval"
    257              case $optval in
    258              [789]|10|11|12)
    259              ;;
    260              *) die Unrecognized Visual Studio Version in $opt
    261              ;;
    262              esac
    263     ;;
    264     --ver=*) vs_ver="$optval"
    265              case $optval in
    266              7) sln_vers="8.00"
    267                 sln_vers_str="Visual Studio .NET 2003"
    268              ;;
    269              [89])
    270              ;;
    271              *) die "Unrecognized Visual Studio Version '$optval' in $opt"
    272              ;;
    273              esac
    274     ;;
    275     --target=*) target="${optval}"
    276     ;;
    277     -*) die_unknown $opt
    278     ;;
    279     *) file_list[${#file_list[@]}]="$opt"
    280     esac
    281 done
    282 outfile=${outfile:-/dev/stdout}
    283 mkoutfile=${mkoutfile:-/dev/stdout}
    284 case "${vs_ver:-8}" in
    285     7) sln_vers="8.00"
    286        sln_vers_str="Visual Studio .NET 2003"
    287     ;;
    288     8) sln_vers="9.00"
    289        sln_vers_str="Visual Studio 2005"
    290     ;;
    291     9) sln_vers="10.00"
    292        sln_vers_str="Visual Studio 2008"
    293     ;;
    294     10) sln_vers="11.00"
    295        sln_vers_str="Visual Studio 2010"
    296     ;;
    297     11) sln_vers="12.00"
    298        sln_vers_str="Visual Studio 2012"
    299     ;;
    300     12) sln_vers="12.00"
    301        sln_vers_str="Visual Studio 2013"
    302     ;;
    303 esac
    304 case "${vs_ver:-8}" in
    305     [789])
    306     sfx=vcproj
    307     ;;
    308     10|11|12)
    309     sfx=vcxproj
    310     ;;
    311 esac
    312 
    313 for f in "${file_list[@]}"; do
    314     parse_project $f
    315 done
    316 cat  >${outfile} <<EOF
    317 Microsoft Visual Studio Solution File, Format Version $sln_vers${EOLDOS}
    318 # $sln_vers_str${EOLDOS}
    319 EOF
    320 for proj in ${proj_list}; do
    321     process_project $proj >>${outfile}
    322 done
    323 process_global >>${outfile}
    324 process_makefile >${mkoutfile}
    325