autobuild (14746B)
1 #!/usr/bin/env sh 2 3 ## 4 ## Installs package dependencies and builds the application. 5 ## 6 7 # Don't exit if some command fails. 8 set +e 9 # Disable file globbing. 10 set -f 11 12 # Boolean variables are true if non-empty and false otherwise. 13 14 # Command to install packages. 15 PKGCMD= 16 # Args to pass to $PKGCMD. 17 PKGARGS= 18 # Required packages. 19 PACKAGES= 20 # Whether package installation requires root permissions. 21 PKG_INSTALL_AS_ROOT=true 22 # Whether to skip package installation altogether. 23 PKG_INSTALL_SKIP= 24 # Whether to force package installation, even if it does not seem 25 # necessary. 26 PKG_INSTALL_FORCE= 27 # Only test if the OS is handled by this script. 28 DRY_RUN= 29 # If and where to install the program. 30 INSTALL_DIR= 31 # Whether we can install packages. 32 OS_IS_HANDLED=true 33 # Which OSs installer to use 34 OS= 35 36 ## +-----------------------------------------------------------+ 37 ## * Utility Functions 38 ## +-----------------------------------------------------------+ 39 40 usage() 41 { 42 cat <<EOF 43 usage:$(basename "$0") [--help|-n|-i DIR|[-d -D]|[--os OS]] 44 45 -n Don't do anything, but check if this OS is handled. 46 47 -i DIR Install the program in the given directory. 48 49 -d Force dependency installattion. 50 51 -D Skip dependency installattion. 52 53 --os OS Use the given OS's installer 54 55 --help Display this message. 56 57 EOF 58 exit "$1" 59 } 60 61 # Search for command $1 in PATH. Print its absolute filename. 62 which() 63 { 64 if [ -z "$1" ]; then 65 return 1 66 fi 67 command -v "$1" 68 } 69 70 # Quote $@ for the shell. 71 quote() 72 { 73 quoted= 74 for arg; do 75 qarg=$(printf "%s" "$arg" | sed -e 's/[|&;<>()$\`"'\'' ]/\\&/g') 76 if [ -z "$quoted" ]; then 77 quoted=$qarg 78 else 79 quoted="$quoted $qarg" 80 fi 81 done 82 printf "%s" "$quoted" 83 } 84 85 # Attempt to exec $@ as root. 86 exec_privileged() { 87 if [ -z "$1" ]; then 88 echo "internal error: command is empty" 89 exit 2 90 fi 91 if [ -w / ]; then 92 "$@" 93 elif which sudo >/dev/null 2>&1; then 94 sudo -- "$@" 95 retval=$? 96 sudo -k 97 return $retval 98 elif which su >/dev/null 2>&1; then 99 su -c "$(quote "$@")" 100 else 101 echo "No such program: sudo or su" 102 exit 1 103 fi 104 } 105 106 # Test if $1 is in PATH or exit with a failure status. 107 assert_program() 108 { 109 if ! which "$1" >/dev/null 2>&1; then 110 echo "No such program: $1" 111 exit 1 112 fi 113 } 114 115 # Source filename $1 and echo variable $2. 116 source_var() 117 { 118 if ! [ -f "$1" ] || ! [ -r "$1" ] || [ -z "$2" ]; then 119 return 1 120 fi 121 # shellcheck source=/dev/null 122 . "$1" 123 eval "printf '%s\n' \$$2" 124 return 0 125 } 126 127 exit_success() 128 { 129 echo "===========================" 130 echo " Build succeeded. :O) " 131 echo "===========================" 132 exit 0 133 } 134 135 exit_fail() 136 { 137 echo "===========================" 138 echo " Build failed. ;o( " 139 echo "===========================" 140 if [ -z "$PKG_INSTALL_FORCE" ]; then 141 echo "Note: maybe try the '-d' option." 142 fi 143 exit 1 144 } 145 146 # Return 0, if all required packages seem to be installed. 147 have_packages_installed() 148 { 149 { 150 which pkg-config || return 1 151 if ! [ -f configure ];then 152 which autoreconf || return 1 153 which automake || return 1 154 fi 155 for lib in libpng glib-2.0 poppler poppler-glib zlib; do 156 pkg-config --exists $lib || return 1 157 done 158 which make || return 1 159 which gcc || which cc || return 1 160 [ $? -eq 0 ] || return 1 161 return 0 162 } >/dev/null 2>&1 163 } 164 165 handle_options() 166 { 167 while [ $# -gt 0 ]; do 168 case $1 in 169 --help) usage 0;; 170 -n) DRY_RUN=true;; 171 -d) PKG_INSTALL_FORCE=true ;; 172 -D) PKG_INSTALL_SKIP=true ;; 173 -i) 174 shift 175 [ $# -gt 0 ] || usage 1 176 if [ "${1%%/}" != "${PWD%%/}" ]; then 177 INSTALL_DIR=$1 178 fi ;; 179 --os) 180 shift 181 [ $# -gt 0 ] || usage 1 182 OS="$1" 183 ;; 184 *) usage 1 ;; 185 esac 186 shift 187 done 188 if [ -n "$PKG_INSTALL_SKIP" ] && [ -n "$PKG_INSTALL_FORCE" ]; then 189 usage 1 190 fi 191 } 192 193 ## +-----------------------------------------------------------+ 194 ## * OS Functions 195 ## +-----------------------------------------------------------+ 196 197 # Archlinux 198 os_arch() { 199 if ! [ -e "/etc/arch-release" ]; then 200 return 1; 201 fi 202 PKGCMD=pacman 203 PKGARGS="-S --needed" 204 PACKAGES="base-devel libpng zlib poppler-glib" 205 return 0; 206 } 207 208 # CentOS 209 os_centos() { 210 if ! [ -e "/etc/centos-release" ]; then 211 return 1 212 fi 213 PKGCMD=yum 214 if yum help install-n >/dev/null 2>&1; then 215 PKGARGS=install-n 216 else 217 PKGARGS=install 218 fi 219 PACKAGES="autoconf 220 automake 221 gcc 222 libpng-devel 223 make 224 pkgconfig 225 poppler-devel 226 poppler-glib-devel 227 zlib-devel" 228 return 0 229 } 230 231 # FreeBSD 232 os_freebsd() { 233 if ! which uname >/dev/null 2>&1 || [ "$(uname -s)" != "FreeBSD" ]; then 234 return 1 235 fi 236 PKGCMD=pkg 237 PKGARGS=install 238 PACKAGES="autotools poppler-glib png pkgconf" 239 return 0 240 } 241 242 # OpenBSD 243 os_openbsd() { 244 if ! which uname >/dev/null 2>&1 || [ "$(uname -s)" != "OpenBSD" ]; then 245 return 1 246 fi 247 PKGCMD=pkg_add 248 PKGARGS="-uU" 249 PACKAGES="autoconf%2.69 automake%1.15 poppler poppler-utils png" 250 export AUTOCONF_VERSION=2.69 251 export AUTOMAKE_VERSION=1.15 252 return 0 253 } 254 255 # Fedora 256 os_fedora() { 257 if ! [ -e "/etc/fedora-release" ]; then 258 return 1 259 fi 260 PKGCMD=dnf 261 PKGARGS=install 262 PACKAGES="autoconf 263 automake 264 gcc 265 libpng-devel 266 make 267 poppler-devel 268 poppler-glib-devel 269 zlib-devel" 270 VERSION=$(source_var /etc/os-release VERSION_ID) 271 if [ -n "$VERSION" ] && [ "$VERSION" -ge 26 ]; then 272 PACKAGES="$PACKAGES pkgconf" 273 else 274 PACKAGES="$PACKAGES pkgconfig" 275 fi 276 return 0 277 } 278 279 # Debian/Ubuntu 280 os_debian() { 281 if ! [ -e "/etc/debian_version" ]; then 282 return 1 283 fi 284 PACKAGES="autoconf 285 automake 286 gcc 287 libpng-dev 288 libpoppler-dev 289 libpoppler-glib-dev 290 libz-dev 291 make 292 pkg-config" 293 PKGCMD=apt-get 294 PKGARGS="install -y" 295 return 0 296 } 297 298 # Msys2 299 os_msys2() { 300 if [ -z "$MSYSTEM" ] || ! [ -r "/etc/profile" ]; then 301 return 1 302 fi 303 case $MSYSTEM in 304 MINGW64) 305 PACKAGES="base-devel 306 autoconf 307 automake 308 mingw-w64-x86_64-libpng 309 mingw-w64-x86_64-poppler 310 mingw-w64-x86_64-imagemagick 311 mingw-w64-x86_64-toolchain 312 mingw-w64-x86_64-openssl 313 mingw-w64-x86_64-zlib" ;; 314 MINGW32) 315 PACKAGES="base-devel 316 autoconf 317 automake 318 mingw-w64-i686-libpng 319 mingw-w64-i686-poppler 320 mingw-w64-i686-imagemagick 321 mingw-w64-i686-toolchain 322 mingw-w64-i686-openssl 323 mingw-w64-i686-zlib" ;; 324 MSYS) 325 case $(uname -m) in 326 x86_64) 327 MSYSTEM=MINGW64 ;; 328 *) 329 MSYSTEM=MINGW32 ;; 330 esac 331 export MSYSTEM 332 # shellcheck source=/dev/null 333 . /etc/profile 334 eval "exec $(quote "$0" "$@")" ;; 335 *) 336 echo "Unrecognized MSYSTEM value: $MSYSTEM" 337 exit 1 ;; 338 esac 339 PKGCMD=pacman 340 PKGARGS="-S --needed" 341 PKG_INSTALL_AS_ROOT= 342 return 0 343 } 344 345 # MacOS 346 os_macos() { 347 if ! which uname >/dev/null 2>&1 || [ "$(uname -s)" != "Darwin" ]; then 348 return 1 349 elif which brew >/dev/null 2>&1; then 350 PKGCMD=brew 351 PKGARGS=install 352 PACKAGES="pkg-config poppler autoconf automake" 353 PKG_INSTALL_AS_ROOT= 354 # brew installs libffi as keg-only, meaning we need to set 355 # PKG_CONFIG_PATH manually so configure can find it 356 export PKG_CONFIG_PATH="${PKG_CONFIG_PATH}:$(brew --prefix libffi)/lib/pkgconfig/:$(brew --prefix zlib)/lib/pkgconfig/" 357 elif which port >/dev/null 2>&1; then 358 PKGCMD=port 359 PKGARGS=install 360 PACKAGES="pkgconfig poppler autoconf automake libpng" 361 else 362 return 1 363 fi 364 return 0 365 } 366 367 # NixOS 368 os_nixos() { 369 # Already in the nix-shell. 370 if [ -n "$AUTOBUILD_NIX_SHELL" ]; then 371 return 0 372 fi 373 if ! which nix-shell >/dev/null 2>&1; then 374 return 1 375 fi 376 if [ -n "$DRY_RUN" ]; then 377 return 0 378 fi 379 if ! nix-instantiate --eval -E "<nixpkgs>" &>/dev/null; then 380 echo "File 'nixpkgs' was not found in the Nix path. Using NixOS/nixpkgs" 381 NIX_PATH="nixpkgs=https://github.com/nixos/nixpkgs/archive/master.tar.gz:$NIX_PATH" 382 fi 383 command="AUTOBUILD_NIX_SHELL=true" 384 command="$command;export AUTOBUILD_NIX_SHELL" 385 command="$command;$(quote "$0" "$@")" 386 exec nix-shell --pure --run "$command" \ 387 -p automake autoconf pkg-config libpng zlib poppler 388 } 389 390 # Gentoo 391 os_gentoo() { 392 if ! [ -e "/etc/gentoo-release" ]; then 393 return 1 394 fi 395 PKGCMD=emerge 396 PKGARGS=--noreplace 397 PACKAGES="app-text/poppler 398 dev-util/pkgconf 399 media-libs/libpng 400 sys-devel/autoconf 401 sys-devel/automake 402 sys-devel/gcc 403 sys-devel/make 404 sys-libs/glibc 405 sys-libs/zlib" 406 return 0 407 } 408 409 # Void 410 os_void() { 411 if [ -f "/etc/os-release" ]; then 412 . /etc/os-release 413 if [ "$NAME" != "void" ]; then 414 return 1 415 fi 416 else 417 return 1 418 fi 419 PACKAGES="autoconf 420 automake 421 libpng-devel 422 poppler-devel 423 poppler-glib-devel 424 zlib-devel 425 make 426 pkgconf" 427 PKGCMD=xbps-install 428 PKGARGS="-Sy" 429 return 0 430 } 431 432 # openSUSE (TODO: add support for micro versions) 433 os_opensuse() { 434 if [ -f "/etc/os-release" ]; then 435 . /etc/os-release 436 if [ "$ID" != "opensuse-leap" ] && [ "$ID" != "opensuse-tumbleweed" ]; then 437 return 1 438 fi 439 else 440 return 1 441 fi 442 PACKAGES="make 443 automake 444 autoconf 445 gcc 446 libpng16-devel 447 libpng16-compat-devel 448 zlib-devel 449 libpoppler-devel 450 libpoppler-glib-devel 451 glib2-devel 452 pkgconf" 453 PKGCMD=zypper 454 PKGARGS="install" 455 return 0 456 } 457 458 # Alpine Linux 459 os_alpine() { 460 if [ -f "/etc/os-release" ]; then 461 . /etc/os-release 462 if [ "$ID" != "alpine" ]; then 463 return 1 464 fi 465 else 466 return 1 467 fi 468 PACKAGES="autoconf 469 automake 470 libpng-dev 471 poppler-dev 472 glib-dev 473 gcc 474 build-base" 475 PKGCMD=apk 476 PKGARGS="add" 477 return 0 478 } 479 480 # By Parameter --os 481 os_argument() { 482 [ -z "$OS" ] && return 1 483 case $OS in 484 macos) os_macos "$@";; 485 freebsd) os_freebsd "$@";; 486 arch) os_arch "$@";; 487 centos) os_centos "$@";; 488 openbsd) os_openbsd "$@";; 489 fedora) os_fedora "$@";; 490 debian) os_debian "$@";; 491 gentoo) os_gentoo "$@";; 492 msys2) os_msys2 "$@";; 493 nixos) os_nixos "$@";; 494 void) os_void "$@";; 495 opensuse) os_opensuse "$@";; 496 alpine) os_alpine "$@";; 497 *) echo "Invalid --os argument: $OS" 498 exit 1 499 esac || { 500 echo "Unable to install on this system as $OS" 501 exit 1 502 } 503 } 504 505 ## +-----------------------------------------------------------+ 506 ## * Figure out where we are 507 ## ** install deps and build the program 508 ## +-----------------------------------------------------------+ 509 510 handle_options "$@" 511 512 os_argument "$@" || \ 513 os_macos "$@" || \ 514 os_freebsd "$@" || \ 515 os_arch "$@" || \ 516 os_centos "$@" || \ 517 os_openbsd "$@" || \ 518 os_fedora "$@" || \ 519 os_debian "$@" || \ 520 os_gentoo "$@" || \ 521 os_msys2 "$@" || \ 522 os_nixos "$@" || \ 523 os_void "$@" || \ 524 os_opensuse "$@" || \ 525 os_alpine "$@" || \ 526 { 527 OS_IS_HANDLED= 528 if [ -z "$DRY_RUN" ]; then 529 echo "Failed to recognize this system, trying to continue." 530 fi 531 } 532 533 if [ -n "$DRY_RUN" ]; then 534 [ -n "$OS_IS_HANDLED" ] 535 exit $? 536 fi 537 538 if [ -n "$PKGCMD" ];then 539 echo "---------------------------" 540 echo " Installing packages " 541 echo "---------------------------" 542 if [ -n "$PKG_INSTALL_SKIP" ]; then 543 echo "Skipping package installation (as requested)" 544 elif [ -z "$PKG_INSTALL_FORCE" ] && have_packages_installed; then 545 echo "Skipping package installation (already installed)" 546 else 547 assert_program "$PKGCMD" 548 echo "$PKGCMD $PKGARGS $PACKAGES" 549 if [ -n "$PKG_INSTALL_AS_ROOT" ]; then 550 exec_privileged $PKGCMD $PKGARGS $PACKAGES 551 else 552 $PKGCMD $PKGARGS $PACKAGES 553 fi 554 fi 555 echo 556 fi 557 558 # Try to be in the correct directory. 559 if which dirname >/dev/null 2>&1; then 560 cd "$(dirname "$0")" || { 561 echo "Failed to change into the source directory" 562 exit 1 563 } 564 fi 565 566 echo "---------------------------" 567 echo " Configuring and compiling " 568 echo "---------------------------" 569 570 # Create the configure script. 571 if ! [ -f ./configure ]; then 572 assert_program autoreconf 573 echo "autoreconf -i" 574 autoreconf -i 575 [ -f ./configure ] || exit_fail 576 fi 577 578 # Build the program. 579 if [ -n "$INSTALL_DIR" ]; then 580 prefix=--bindir=$INSTALL_DIR 581 fi 582 583 echo "./configure -q $prefix && make clean && make -s" 584 eval "./configure -q $(quote "$prefix") && make clean && make -s || exit_fail" 585 echo 586 if [ -n "$INSTALL_DIR" ]; then 587 echo "---------------------------" 588 echo " Installing " 589 echo "---------------------------" 590 echo make -s install 591 if mkdir -p -- "$INSTALL_DIR" && [ -w "$INSTALL_DIR" ]; then 592 make install || exit_fail 593 else 594 exec_privileged make install || exit_fail 595 fi 596 # Copy dynamic libraries on windows. 597 if [ -f epdfinfo.exe ]; then 598 assert_program awk 599 assert_program ldd 600 for dll in $(ldd epdfinfo.exe | awk '/\/mingw/ {print $3}'); do 601 cp -u "$dll" "$INSTALL_DIR" 602 done 603 fi 604 echo 605 fi 606 exit_success 607 608 # Local Variables: 609 # compile-command: "shellcheck autobuild" 610 # End: