Compare commits

..
Author SHA1 Message Date
Christopher Sean Morrison c6e93f43fb remove frozen branches that were 'completed' (or dead/closed) including the ansi, autoconf, bobWinPort, brlcad_5_1_alpha_patch, photonmap, and windows branches (svn branch delete)
svn:revision:30690
svn:branch:windows-branch
svn:account:brlcad
2008-04-16 15:10:30 +00:00
Christopher Sean Morrison a1a0150fef remerge head into branch just in case someone checks out this branch later
svn:revision:22531
cvs:account:morrison
cvs:branch:windows-branch
2004-03-17 04:15:12 +00:00
Christopher Sean Morrison 6720a43e3a merge from head
svn:revision:22506
cvs:account:morrison
cvs:branch:windows-branch
2004-03-15 20:17:09 +00:00
Christopher Sean Morrison 037b7fcbab simplify defines for windows
svn:revision:22503
cvs:account:morrison
cvs:branch:windows-branch
2004-03-15 17:49:02 +00:00
Christopher Sean Morrison 70ff21db2e reformat and readd missing semicolon
svn:revision:22482
cvs:account:morrison
cvs:branch:windows-branch
2004-03-12 17:40:59 +00:00
Christopher Sean Morrison 7406e4a5dc unbust Cakefile
svn:revision:22481
cvs:account:morrison
cvs:branch:windows-branch
2004-03-12 17:39:31 +00:00
Christopher Sean Morrison 72e1fabdb4 use the define instead of the hard-coded constant
svn:revision:22480
cvs:account:morrison
cvs:branch:windows-branch
2004-03-12 17:38:48 +00:00
Christopher Sean Morrison be4db36c6e ws and missing variables after merge
svn:revision:22479
cvs:account:morrison
cvs:branch:windows-branch
2004-03-12 17:37:44 +00:00
Christopher Sean Morrison ccaa43c5c9 use RT_MAXLINE instead of the constant -- same purpose really
svn:revision:22478
cvs:account:morrison
cvs:branch:windows-branch
2004-03-12 17:37:09 +00:00
Christopher Sean Morrison 8a3a9ec743 use strcasecmp instead of stricmp if it is available, strcasecmp is bsd 4.4 stricmp is not
svn:revision:22477
cvs:account:morrison
cvs:branch:windows-branch
2004-03-12 17:26:12 +00:00
Christopher Sean Morrison 2947257518 check for strcasecmp
svn:revision:22476
cvs:account:morrison
cvs:branch:windows-branch
2004-03-12 17:24:38 +00:00
Christopher Sean Morrison cd4069485b fix merge bug and revert back to using RT_MAXLINE instead of hard-coded constants
svn:revision:22475
cvs:account:morrison
cvs:branch:windows-branch
2004-03-12 15:04:01 +00:00
Christopher Sean Morrison 72f97f8a2d unsnafu machine defines that were obliterated
svn:revision:22474
cvs:account:morrison
cvs:branch:windows-branch
2004-03-12 14:13:59 +00:00
Christopher Sean Morrison ccd86d04f7 merge from HEAD
svn:revision:22473
cvs:account:morrison
cvs:branch:windows-branch
2004-03-12 10:01:24 +00:00
Christopher Sean Morrison ded045c892 join with HEAD
svn:revision:22471
cvs:account:morrison
cvs:branch:windows-branch
2004-03-12 07:04:39 +00:00
Christopher Sean Morrison b0e9de545f join with HEAD
svn:revision:22470
cvs:account:morrison
cvs:branch:windows-branch
2004-03-12 07:03:37 +00:00
Christopher Sean Morrison f96486150e join with HEAD
svn:revision:22469
cvs:account:morrison
cvs:branch:windows-branch
2004-03-12 07:02:34 +00:00
Christopher Sean Morrison 7e2df94d49 sync to HEAD...
svn:revision:22468
cvs:account:morrison
cvs:branch:windows-branch
2004-03-11 23:52:42 +00:00
Christopher Sean Morrison 4af92bc5d6 sync to HEAD...
svn:revision:22468
cvs:branch:windows-branch
cvs:account:morrison
2004-03-11 23:47:37 +00:00
Christopher Sean Morrison c21acdd559 sync to HEAD...
svn:revision:22468
cvs:branch:windows-branch
cvs:account:morrison
2004-03-11 23:42:13 +00:00
Christopher Sean Morrison b1650f4049 merge in updates from HEAD
svn:revision:22463
cvs:account:morrison
cvs:branch:windows-branch
2004-03-10 15:06:37 +00:00
Christopher Sean Morrison 32fd846a05 Survice Engineering patch to clean up the build environment and several runtime issues
svn:revision:22003
cvs:account:morrison
cvs:branch:windows-branch
2003-08-14 08:07:27 +00:00
Christopher Sean Morrison 190f904c64 removed comment embedded in comment and added trailing newline to file that got lost
svn:revision:21637
cvs:account:morrison
cvs:branch:windows-branch
2002-09-27 01:22:57 +00:00
Christopher Sean Morrison b9a40e9d85 realised that they clobbered out the other architectures... need to manually remerge with the full conf.h by hand.
svn:revision:21636
cvs:account:morrison
cvs:branch:windows-branch
2002-09-27 01:22:08 +00:00
Christopher Sean Morrison 4bce14dff7 Modifications (on a 6.0 source distribution) for initial port to windows (merged with sources close to 6.0.2)
svn:revision:21635
cvs:branch:windows-branch
cvs:account:morrison
2002-09-26 23:04:21 +00:00
Robert Parker 096c109ece Import itcl3.2
svn:revision:19762
svn:revision:19763
cvs:account:bparker
cvs:branch:itcl3-2
2000-12-06 21:48:10 +00:00
Robert Parker e078a68d77 Import itcl3.2
svn:revision:19760
svn:revision:19761
cvs:account:bparker
cvs:branch:itcl3-2
2000-12-06 21:35:20 +00:00
Robert Parker 0287a35ffb Import tk8.3
svn:revision:19758
svn:revision:19759
cvs:account:bparker
cvs:branch:tk8-3
2000-12-06 21:34:21 +00:00
Robert Parker e77989c21b Import tcl8.3
svn:revision:19756
svn:revision:19757
cvs:account:bparker
cvs:branch:tcl8-3
2000-12-06 21:33:21 +00:00
Lee Butler 9c696591dd The html manuals for BRLCAD
svn:revision:15427
cvs:account:butler
cvs:branch:VendorARL
1998-06-30 17:38:07 +00:00
John Anderson bf843475ea libpng 1.0.2
svn:revision:15365
cvs:account:jra
cvs:branch:libpng
1998-06-24 20:00:14 +00:00
John Anderson e63f8fccee Initial inclusion of zlib (version 1.0.4).
svn:revision:15338
cvs:account:jra
cvs:branch:zlib
1998-06-24 13:19:59 +00:00
John Anderson 13e0bb1a11 Checkpoint
svn:revision:8061
cvs:account:jra
cvs:branch:unlabeled-1.1.1
1993-12-09 09:52:56 +00:00
John Anderson e83e56b866 Checkpoint
svn:revision:7885
cvs:account:jra
cvs:branch:unlabeled-1.1.1
1993-10-21 15:33:46 +00:00
John Anderson fab2420d37 Checkpoint (working version for just 3DFACE entities).
svn:revision:7884
cvs:account:jra
cvs:branch:unlabeled-1.1.1
1993-10-21 14:14:44 +00:00
Paul Tanenbaum 6b8c080c36 Attempt to add $Header$ to file.
svn:revision:5208
cvs:branch:unlabeled-1.1.1
cvs:account:pjt
1991-02-14 09:24:53 +00:00
12734 changed files with 2117845 additions and 3024177 deletions
-2
View File
@@ -1,2 +0,0 @@
# Try to tell GitHub how to handle .asc files
*.asc linguist-language=Tcl
-260
View File
@@ -1,260 +0,0 @@
name: Prepare bext dependencies
description: Restore a compatible bext production artifact or build the pinned revision.
inputs:
platform-channel:
description: Published bext platform channel.
required: true
source-dir:
description: Absolute path to the BRL-CAD source tree.
required: true
output-dir:
description: Absolute path where the bext dependency tree will be prepared.
required: true
build-type:
description: BRL-CAD build configuration that will consume the dependency tree.
required: false
default: Release
artifact-token:
description: Token with Actions read access to BRL-CAD/bext.
required: false
outputs:
bext-sha:
description: The bext revision in the prepared dependency tree.
value: ${{ steps.result.outputs.bext-sha }}
source:
description: Whether preparation used a production artifact, cache, or local build.
value: ${{ steps.result.outputs.source }}
runs:
using: composite
steps:
- name: Resolve bext production artifact
id: resolve
shell: bash
env:
BEXT_BUILD_TYPE: ${{ inputs.build-type }}
BEXT_CHANNEL: ${{ inputs.platform-channel }}
BRLCAD_SOURCE_DIR: ${{ inputs.source-dir }}
GH_TOKEN: ${{ inputs.artifact-token }}
run: |
set -uo pipefail
source_dir="$BRLCAD_SOURCE_DIR"
if command -v cygpath >/dev/null 2>&1; then
source_dir="$(cygpath -u "$source_dir")"
fi
required_sha="$(awk -F'[()]' '/^[[:space:]]*brlcad_bext_init\([0-9a-fA-F]{40}\)/ { print tolower($2) }' "$source_dir/CMakeLists.txt")"
if [[ ! "$required_sha" =~ ^[0-9a-f]{40}$ ]]; then
echo "Expected exactly one brlcad_bext_init(<sha>) call in $source_dir/CMakeLists.txt" >&2
exit 1
fi
repository='BRL-CAD/bext'
marker_name="bext-production-$required_sha"
marker_info="$(gh api "repos/$repository/actions/artifacts?name=$marker_name&per_page=100" \
--jq '[.artifacts[] | select(.expired == false and .name == "'"$marker_name"'")] | sort_by(.created_at) | last | select(. != null) | [.name, .workflow_run.id] | @tsv' 2>/dev/null)" || marker_info=''
selected_sha=''
run_id=''
if [[ -n "$marker_info" ]]; then
selected_sha="$required_sha"
IFS=$'\t' read -r _ run_id <<< "$marker_info"
echo "Found complete bext production artifacts for pinned revision $required_sha."
else
marker_info="$(gh api "repos/$repository/actions/artifacts?per_page=100" \
--jq '[.artifacts[] | select(.expired == false and (.name | test("^bext-production-[0-9a-f]{40}$")))] | sort_by(.created_at) | last | select(. != null) | [.name, .workflow_run.id] | @tsv' 2>/dev/null)" || marker_info=''
if [[ -n "$marker_info" ]]; then
IFS=$'\t' read -r latest_marker run_id <<< "$marker_info"
selected_sha="${latest_marker#bext-production-}"
comparison="$(gh api "repos/$repository/compare/$required_sha...$selected_sha" --jq '.status' 2>/dev/null)" || comparison=''
if [[ "$comparison" == 'ahead' || "$comparison" == 'identical' ]]; then
echo "::warning::Using newer successful bext revision $selected_sha instead of BRL-CAD's pinned revision $required_sha."
else
selected_sha=''
run_id=''
fi
fi
fi
artifact_ready=false
artifact_name=''
if [[ "$RUNNER_OS" == 'Windows' && "$BEXT_BUILD_TYPE" == 'Debug' ]]; then
echo 'Windows Debug requires a Debug bext build; skipping Release production artifacts.'
selected_sha=''
run_id=''
elif [[ -n "$selected_sha" ]]; then
artifact_name="bext-$BEXT_CHANNEL-$selected_sha"
artifact_count="$(gh api "repos/$repository/actions/runs/$run_id/artifacts?name=$artifact_name&per_page=100" \
--jq '[.artifacts[] | select(.expired == false and .name == "'"$artifact_name"'")] | length' 2>/dev/null)" || artifact_count=0
if [[ "$artifact_count" == '1' ]]; then
artifact_ready=true
else
selected_sha=''
run_id=''
artifact_name=''
fi
fi
cache_schema=1
image_version="${ImageVersion:-unknown}"
runner_arch="${RUNNER_ARCH:-unknown}"
fallback_cache_key="bext-$cache_schema-$BEXT_CHANNEL-$BEXT_BUILD_TYPE-$required_sha-$image_version-$runner_arch"
production_cache_key="bext-$cache_schema-$BEXT_CHANNEL-Release-$selected_sha"
if [[ "$artifact_ready" != 'true' ]]; then
echo "No compatible production artifact is available; using the cache/build fallback for $required_sha."
fi
echo "required-sha=$required_sha" >> "$GITHUB_OUTPUT"
echo "selected-sha=$selected_sha" >> "$GITHUB_OUTPUT"
echo "run-id=$run_id" >> "$GITHUB_OUTPUT"
echo "artifact-name=$artifact_name" >> "$GITHUB_OUTPUT"
echo "artifact-ready=$artifact_ready" >> "$GITHUB_OUTPUT"
echo "production-cache-key=$production_cache_key" >> "$GITHUB_OUTPUT"
echo "fallback-cache-key=$fallback_cache_key" >> "$GITHUB_OUTPUT"
- name: Restore production artifact cache
if: steps.resolve.outputs.artifact-ready == 'true'
id: production-cache
uses: actions/cache/restore@v6
with:
path: ${{ inputs.output-dir }}
key: ${{ steps.resolve.outputs.production-cache-key }}
- name: Download bext production artifact
if: steps.resolve.outputs.artifact-ready == 'true' && steps.production-cache.outputs.cache-hit != 'true'
id: download
shell: bash
env:
ARTIFACT_NAME: ${{ steps.resolve.outputs.artifact-name }}
BEXT_CHANNEL: ${{ inputs.platform-channel }}
BEXT_OUTPUT_DIR: ${{ inputs.output-dir }}
BEXT_RUN_ID: ${{ steps.resolve.outputs.run-id }}
GH_TOKEN: ${{ inputs.artifact-token }}
run: |
set -uo pipefail
output_dir="$BEXT_OUTPUT_DIR"
if command -v cygpath >/dev/null 2>&1; then
output_dir="$(cygpath -u "$output_dir")"
fi
download_dir="$RUNNER_TEMP/bext-download-$BEXT_RUN_ID-$BEXT_CHANNEL"
cmake -E rm -rf "$download_dir" "$output_dir"
cmake -E make_directory "$download_dir" "$output_dir"
ready=false
if gh run download "$BEXT_RUN_ID" --repo BRL-CAD/bext --name "$ARTIFACT_NAME" --dir "$download_dir"; then
archive="$download_dir/bext-$BEXT_CHANNEL.tar.gz"
if (cd "$output_dir" && cmake -E tar xzf "$archive") && \
[[ -d "$output_dir/install" && -d "$output_dir/noinstall" && -f "$output_dir/bext-install-manifest.json" ]]; then
ready=true
fi
fi
cmake -E rm -rf "$download_dir"
if [[ "$ready" != 'true' ]]; then
cmake -E rm -rf "$output_dir"
echo '::warning::Unable to download or validate the bext production artifact; using the pinned cache/build fallback.'
fi
echo "ready=$ready" >> "$GITHUB_OUTPUT"
- name: Restore fallback bext cache
if: steps.production-cache.outputs.cache-hit != 'true' && steps.download.outputs.ready != 'true'
id: fallback-cache
uses: actions/cache/restore@v6
with:
path: ${{ inputs.output-dir }}
key: ${{ steps.resolve.outputs.fallback-cache-key }}
- name: Build pinned bext revision
if: steps.production-cache.outputs.cache-hit != 'true' && steps.download.outputs.ready != 'true' && steps.fallback-cache.outputs.cache-hit != 'true'
shell: bash
env:
BEXT_BUILD_TYPE: ${{ inputs.build-type }}
BEXT_OUTPUT_DIR: ${{ inputs.output-dir }}
BEXT_SHA: ${{ steps.resolve.outputs.required-sha }}
run: |
set -euo pipefail
output_dir="$BEXT_OUTPUT_DIR"
if command -v cygpath >/dev/null 2>&1; then
output_dir="$(cygpath -u "$output_dir")"
fi
source_dir="$RUNNER_TEMP/bext-src"
build_dir="$RUNNER_TEMP/bext-build"
cleanup() {
cmake -E rm -rf "$source_dir" "$build_dir"
}
trap cleanup EXIT
cleanup
cmake -E rm -rf "$output_dir"
git clone --filter=blob:none https://github.com/BRL-CAD/bext.git "$source_dir"
git -C "$source_dir" -c advice.detachedHead=false checkout "$BEXT_SHA"
configure_args=(-S "$source_dir" -B "$build_dir" -G Ninja -DENABLE_ALL=ON -DGIT_SHALLOW_CLONE=ON "-DCMAKE_BUILD_TYPE=$BEXT_BUILD_TYPE" "-DCMAKE_INSTALL_PREFIX=$output_dir")
if [[ "$RUNNER_OS" == 'Windows' ]]; then
configure_args+=(-DCMAKE_C_COMPILER=cl.exe -DCMAKE_CXX_COMPILER=cl.exe)
elif [[ "$RUNNER_OS" == 'macOS' ]]; then
export CC=clang
export CXX=clang++
fi
cmake "${configure_args[@]}"
cmake --build "$build_dir" --config "$BEXT_BUILD_TYPE" --parallel 2
- name: Validate bext dependency tree
shell: bash
env:
BEXT_OUTPUT_DIR: ${{ inputs.output-dir }}
run: |
set -euo pipefail
output_dir="$BEXT_OUTPUT_DIR"
if command -v cygpath >/dev/null 2>&1; then
output_dir="$(cygpath -u "$output_dir")"
fi
[[ -d "$output_dir/install" && -d "$output_dir/noinstall" && -f "$output_dir/bext-install-manifest.json" ]]
tool="$output_dir/noinstall/bin/strclear"
if [[ "$RUNNER_OS" == 'Windows' ]]; then
[[ -f "$tool.exe" ]]
else
[[ -x "$tool" ]]
fi
- name: Save production artifact cache
if: steps.download.outputs.ready == 'true'
uses: actions/cache/save@v6
with:
path: ${{ inputs.output-dir }}
key: ${{ steps.resolve.outputs.production-cache-key }}
- name: Save fallback bext cache
if: steps.production-cache.outputs.cache-hit != 'true' && steps.download.outputs.ready != 'true' && steps.fallback-cache.outputs.cache-hit != 'true'
uses: actions/cache/save@v6
with:
path: ${{ inputs.output-dir }}
key: ${{ steps.resolve.outputs.fallback-cache-key }}
- name: Report bext source
id: result
shell: bash
env:
ARTIFACT_READY: ${{ steps.resolve.outputs.artifact-ready }}
ARTIFACT_SHA: ${{ steps.resolve.outputs.selected-sha }}
DOWNLOAD_READY: ${{ steps.download.outputs.ready }}
FALLBACK_CACHE_HIT: ${{ steps.fallback-cache.outputs.cache-hit }}
PRODUCTION_CACHE_HIT: ${{ steps.production-cache.outputs.cache-hit }}
REQUIRED_SHA: ${{ steps.resolve.outputs.required-sha }}
run: |
if [[ "$PRODUCTION_CACHE_HIT" == 'true' ]]; then
source=production-cache
elif [[ "$DOWNLOAD_READY" == 'true' ]]; then
source=production-artifact
elif [[ "$FALLBACK_CACHE_HIT" == 'true' ]]; then
source=fallback-cache
else
source=local-build
fi
if [[ "$ARTIFACT_READY" == 'true' && ( "$PRODUCTION_CACHE_HIT" == 'true' || "$DOWNLOAD_READY" == 'true' ) ]]; then
sha="$ARTIFACT_SHA"
else
sha="$REQUIRED_SHA"
fi
echo "source=$source" >> "$GITHUB_OUTPUT"
echo "bext-sha=$sha" >> "$GITHUB_OUTPUT"
echo "Prepared bext $sha from $source."
-637
View File
@@ -1,637 +0,0 @@
# BRL-CAD's primary distcheck target runs too long and does too much work to
# be suitable as a CI target, even occasionally. To achieve essentially the
# same result, we define individual jobs for each distcheck sub-target and
# distribute them across five serial queues. To avoid the target list going
# stale, this header is followed by jobs generated from the CMake logic.
name: Distcheck
on:
workflow_dispatch:
schedule:
- cron: '30 3 * * 5'
jobs:
bext:
name: Prepare bext
runs-on: ubuntu-24.04
env:
DEBIAN_FRONTEND: noninteractive
steps:
- name: Setup - CMake
uses: lukka/get-cmake@latest
- name: Install apt dependencies
run: |
sudo apt-get update
# Install X/OpenGL dev pkgs
sudo apt-get install xserver-xorg-dev libx11-dev libxi-dev libxext-dev libglu1-mesa-dev libfontconfig-dev
# Install tools
sudo apt-get install astyle re2c
# Install dependency dev pkgs
sudo apt-get install zlib1g-dev libpng-dev libjpeg-dev libtiff-dev libeigen3-dev libgdal-dev libassimp-dev libopencv-dev tcl-dev tk-dev
# Install XCB/OpenGL dev pkgs for Qt - see:
# https://wiki.qt.io/Building_Qt_6_from_Git
# https://doc.qt.io/qt-6/linux-requirements.html
sudo apt-get install libfontconfig1-dev libfreetype6-dev libx11-dev libx11-xcb-dev libxext-dev libxfixes-dev libxi-dev libxrender-dev libxcb1-dev libxcb-cursor-dev libxcb-glx0-dev libxcb-keysyms1-dev libxcb-image0-dev libxcb-shm0-dev libxcb-icccm4-dev libxcb-sync-dev libxcb-xfixes0-dev libxcb-shape0-dev libxcb-randr0-dev libxcb-render-util0-dev libxcb-util-dev libxcb-xinerama0-dev libxcb-xkb-dev libxcb-xinput-dev libxcb-xrm-dev libxkbcommon-dev libxkbcommon-x11-dev
sudo apt-get install libgl-dev
sudo apt-get install libinput-dev
- name: Checkout
uses: actions/checkout@v6
with:
path: brlcad
- name: Prepare bext dependencies
uses: ./brlcad/.github/actions/prepare-bext
with:
platform-channel: ubuntu-24.04-${{ runner.arch }}-release
source-dir: ${{ github.workspace }}/brlcad
output-dir: ${{ runner.temp }}/bext_output
build-type: Release
artifact-token: ${{ secrets.BEXT_ARTIFACT_TOKEN }}
distcheck-default_build_type:
name: distcheck-default_build_type
runs-on: ubuntu-24.04
needs: [bext]
env:
DEBIAN_FRONTEND: noninteractive
if: ${{ !cancelled() && github.ref == 'refs/heads/main' }}
steps:
- name: Setup - CMake
uses: lukka/get-cmake@latest
- name: Install apt dependencies
run: |
sudo apt-get update
sudo apt-get install xserver-xorg-dev libx11-dev libxi-dev libxext-dev libglu1-mesa-dev libfontconfig-dev
sudo apt-get install astyle re2c
sudo apt-get install zlib1g-dev libpng-dev libjpeg-dev libtiff-dev libeigen3-dev libgdal-dev libassimp-dev libopencv-dev tcl-dev tk-dev libgl-dev libinput-dev
- name: Checkout
uses: actions/checkout@v6
with:
path: brlcad
- name: Prepare bext dependencies
uses: ./brlcad/.github/actions/prepare-bext
with:
platform-channel: ubuntu-24.04-${{ runner.arch }}-release
source-dir: ${{ github.workspace }}/brlcad
output-dir: ${{ runner.temp }}/bext_output
build-type: Release
artifact-token: ${{ secrets.BEXT_ARTIFACT_TOKEN }}
- name: Directory setup
run: cmake -E make_directory build_distcheck-default_build_type
- name: Configure
run: cmake -S brlcad -B build_distcheck-default_build_type -G Ninja -DBRLCAD_EXT_DIR=${{ runner.temp }}/bext_output
- name: Build
run: cmake --build build_distcheck-default_build_type --target distcheck-default_build_type
- name: Log
if: always()
run: cat build_distcheck-default_build_type/distcheck-default_build_type.log
distcheck-debug:
name: distcheck-debug
runs-on: ubuntu-24.04
needs: [bext]
env:
DEBIAN_FRONTEND: noninteractive
if: ${{ !cancelled() && github.ref == 'refs/heads/main' }}
steps:
- name: Setup - CMake
uses: lukka/get-cmake@latest
- name: Install apt dependencies
run: |
sudo apt-get update
sudo apt-get install xserver-xorg-dev libx11-dev libxi-dev libxext-dev libglu1-mesa-dev libfontconfig-dev
sudo apt-get install astyle re2c
sudo apt-get install zlib1g-dev libpng-dev libjpeg-dev libtiff-dev libeigen3-dev libgdal-dev libassimp-dev libopencv-dev tcl-dev tk-dev libgl-dev libinput-dev
- name: Checkout
uses: actions/checkout@v6
with:
path: brlcad
- name: Prepare bext dependencies
uses: ./brlcad/.github/actions/prepare-bext
with:
platform-channel: ubuntu-24.04-${{ runner.arch }}-release
source-dir: ${{ github.workspace }}/brlcad
output-dir: ${{ runner.temp }}/bext_output
build-type: Release
artifact-token: ${{ secrets.BEXT_ARTIFACT_TOKEN }}
- name: Directory setup
run: cmake -E make_directory build_distcheck-debug
- name: Configure
run: cmake -S brlcad -B build_distcheck-debug -G Ninja -DCMAKE_BUILD_TYPE=Debug -DBRLCAD_EXT_DIR=${{ runner.temp }}/bext_output
- name: Build
run: cmake --build build_distcheck-debug --config Debug --target distcheck-debug
- name: Log
if: always()
run: cat build_distcheck-debug/distcheck-debug.log
distcheck-release:
name: distcheck-release
runs-on: ubuntu-24.04
needs: [bext]
env:
DEBIAN_FRONTEND: noninteractive
if: ${{ !cancelled() && github.ref == 'refs/heads/main' }}
steps:
- name: Setup - CMake
uses: lukka/get-cmake@latest
- name: Install apt dependencies
run: |
sudo apt-get update
sudo apt-get install xserver-xorg-dev libx11-dev libxi-dev libxext-dev libglu1-mesa-dev libfontconfig-dev
sudo apt-get install astyle re2c
sudo apt-get install zlib1g-dev libpng-dev libjpeg-dev libtiff-dev libeigen3-dev libgdal-dev libassimp-dev libopencv-dev tcl-dev tk-dev libgl-dev libinput-dev
- name: Checkout
uses: actions/checkout@v6
with:
path: brlcad
- name: Prepare bext dependencies
uses: ./brlcad/.github/actions/prepare-bext
with:
platform-channel: ubuntu-24.04-${{ runner.arch }}-release
source-dir: ${{ github.workspace }}/brlcad
output-dir: ${{ runner.temp }}/bext_output
build-type: Release
artifact-token: ${{ secrets.BEXT_ARTIFACT_TOKEN }}
- name: Directory setup
run: cmake -E make_directory build_distcheck-release
- name: Configure
run: cmake -S brlcad -B build_distcheck-release -G Ninja -DCMAKE_BUILD_TYPE=Release -DBRLCAD_EXT_DIR=${{ runner.temp }}/bext_output
- name: Build
run: cmake --build build_distcheck-release --config Release --target distcheck-release
- name: Log
if: always()
run: cat build_distcheck-release/distcheck-release.log
distcheck-no_unity_debug:
name: distcheck-no_unity_debug
runs-on: ubuntu-24.04
needs: [bext]
env:
DEBIAN_FRONTEND: noninteractive
if: ${{ !cancelled() && github.ref == 'refs/heads/main' }}
steps:
- name: Setup - CMake
uses: lukka/get-cmake@latest
- name: Install apt dependencies
run: |
sudo apt-get update
sudo apt-get install xserver-xorg-dev libx11-dev libxi-dev libxext-dev libglu1-mesa-dev libfontconfig-dev
sudo apt-get install astyle re2c
sudo apt-get install zlib1g-dev libpng-dev libjpeg-dev libtiff-dev libeigen3-dev libgdal-dev libassimp-dev libopencv-dev tcl-dev tk-dev libgl-dev libinput-dev
- name: Checkout
uses: actions/checkout@v6
with:
path: brlcad
- name: Prepare bext dependencies
uses: ./brlcad/.github/actions/prepare-bext
with:
platform-channel: ubuntu-24.04-${{ runner.arch }}-release
source-dir: ${{ github.workspace }}/brlcad
output-dir: ${{ runner.temp }}/bext_output
build-type: Release
artifact-token: ${{ secrets.BEXT_ARTIFACT_TOKEN }}
- name: Directory setup
run: cmake -E make_directory build_distcheck-no_unity_debug
- name: Configure
run: cmake -S brlcad -B build_distcheck-no_unity_debug -G Ninja -DCMAKE_BUILD_TYPE=Debug -DBRLCAD_EXT_DIR=${{ runner.temp }}/bext_output -DBRLCAD_ENABLE_UNITY_BUILD=OFF
- name: Build
run: cmake --build build_distcheck-no_unity_debug --config Debug --target distcheck-no_unity_debug
- name: Log
if: always()
run: cat build_distcheck-no_unity_debug/distcheck-no_unity_debug.log
distcheck-no_unity_release:
name: distcheck-no_unity_release
runs-on: ubuntu-24.04
needs: [bext]
env:
DEBIAN_FRONTEND: noninteractive
if: ${{ !cancelled() && github.ref == 'refs/heads/main' }}
steps:
- name: Setup - CMake
uses: lukka/get-cmake@latest
- name: Install apt dependencies
run: |
sudo apt-get update
sudo apt-get install xserver-xorg-dev libx11-dev libxi-dev libxext-dev libglu1-mesa-dev libfontconfig-dev
sudo apt-get install astyle re2c
sudo apt-get install zlib1g-dev libpng-dev libjpeg-dev libtiff-dev libeigen3-dev libgdal-dev libassimp-dev libopencv-dev tcl-dev tk-dev libgl-dev libinput-dev
- name: Checkout
uses: actions/checkout@v6
with:
path: brlcad
- name: Prepare bext dependencies
uses: ./brlcad/.github/actions/prepare-bext
with:
platform-channel: ubuntu-24.04-${{ runner.arch }}-release
source-dir: ${{ github.workspace }}/brlcad
output-dir: ${{ runner.temp }}/bext_output
build-type: Release
artifact-token: ${{ secrets.BEXT_ARTIFACT_TOKEN }}
- name: Directory setup
run: cmake -E make_directory build_distcheck-no_unity_release
- name: Configure
run: cmake -S brlcad -B build_distcheck-no_unity_release -G Ninja -DCMAKE_BUILD_TYPE=Release -DBRLCAD_EXT_DIR=${{ runner.temp }}/bext_output -DBRLCAD_ENABLE_UNITY_BUILD=OFF
- name: Build
run: cmake --build build_distcheck-no_unity_release --config Release --target distcheck-no_unity_release
- name: Log
if: always()
run: cat build_distcheck-no_unity_release/distcheck-no_unity_release.log
distcheck-enableall_debug:
name: distcheck-enableall_debug
runs-on: ubuntu-24.04
needs: [distcheck-default_build_type]
env:
DEBIAN_FRONTEND: noninteractive
if: ${{ !cancelled() && github.ref == 'refs/heads/main' }}
steps:
- name: Setup - CMake
uses: lukka/get-cmake@latest
- name: Install apt dependencies
run: |
sudo apt-get update
sudo apt-get install xserver-xorg-dev libx11-dev libxi-dev libxext-dev libglu1-mesa-dev libfontconfig-dev
sudo apt-get install astyle re2c
sudo apt-get install zlib1g-dev libpng-dev libjpeg-dev libtiff-dev libeigen3-dev libgdal-dev libassimp-dev libopencv-dev tcl-dev tk-dev libgl-dev libinput-dev
- name: Checkout
uses: actions/checkout@v6
with:
path: brlcad
- name: Prepare bext dependencies
uses: ./brlcad/.github/actions/prepare-bext
with:
platform-channel: ubuntu-24.04-${{ runner.arch }}-release
source-dir: ${{ github.workspace }}/brlcad
output-dir: ${{ runner.temp }}/bext_output
build-type: Release
artifact-token: ${{ secrets.BEXT_ARTIFACT_TOKEN }}
- name: Directory setup
run: cmake -E make_directory build_distcheck-enableall_debug
- name: Configure
run: cmake -S brlcad -B build_distcheck-enableall_debug -G Ninja -DCMAKE_BUILD_TYPE=Debug -DENABLE_ALL=ON -DBRLCAD_EXT_DIR=${{ runner.temp }}/bext_output
- name: Build
run: cmake --build build_distcheck-enableall_debug --config Debug --target distcheck-enableall_debug
- name: Log
if: always()
run: cat build_distcheck-enableall_debug/distcheck-enableall_debug.log
distcheck-enableall_release:
name: distcheck-enableall_release
runs-on: ubuntu-24.04
needs: [distcheck-debug]
env:
DEBIAN_FRONTEND: noninteractive
if: ${{ !cancelled() && github.ref == 'refs/heads/main' }}
steps:
- name: Setup - CMake
uses: lukka/get-cmake@latest
- name: Install apt dependencies
run: |
sudo apt-get update
sudo apt-get install xserver-xorg-dev libx11-dev libxi-dev libxext-dev libglu1-mesa-dev libfontconfig-dev
sudo apt-get install astyle re2c
sudo apt-get install zlib1g-dev libpng-dev libjpeg-dev libtiff-dev libeigen3-dev libgdal-dev libassimp-dev libopencv-dev tcl-dev tk-dev libgl-dev libinput-dev
- name: Checkout
uses: actions/checkout@v6
with:
path: brlcad
- name: Prepare bext dependencies
uses: ./brlcad/.github/actions/prepare-bext
with:
platform-channel: ubuntu-24.04-${{ runner.arch }}-release
source-dir: ${{ github.workspace }}/brlcad
output-dir: ${{ runner.temp }}/bext_output
build-type: Release
artifact-token: ${{ secrets.BEXT_ARTIFACT_TOKEN }}
- name: Directory setup
run: cmake -E make_directory build_distcheck-enableall_release
- name: Configure
run: cmake -S brlcad -B build_distcheck-enableall_release -G Ninja -DCMAKE_BUILD_TYPE=Release -DENABLE_ALL=ON -DBRLCAD_EXT_DIR=${{ runner.temp }}/bext_output
- name: Build
run: cmake --build build_distcheck-enableall_release --config Release --target distcheck-enableall_release
- name: Log
if: always()
run: cat build_distcheck-enableall_release/distcheck-enableall_release.log
distcheck-prepared_debug:
name: distcheck-prepared_debug
runs-on: ubuntu-24.04
needs: [distcheck-release]
env:
DEBIAN_FRONTEND: noninteractive
if: ${{ !cancelled() && github.ref == 'refs/heads/main' }}
steps:
- name: Setup - CMake
uses: lukka/get-cmake@latest
- name: Install apt dependencies
run: |
sudo apt-get update
sudo apt-get install xserver-xorg-dev libx11-dev libxi-dev libxext-dev libglu1-mesa-dev libfontconfig-dev
sudo apt-get install astyle re2c
sudo apt-get install zlib1g-dev libpng-dev libjpeg-dev libtiff-dev libeigen3-dev libgdal-dev libassimp-dev libopencv-dev tcl-dev tk-dev libgl-dev libinput-dev
- name: Checkout
uses: actions/checkout@v6
with:
path: brlcad
- name: Prepare bext dependencies
uses: ./brlcad/.github/actions/prepare-bext
with:
platform-channel: ubuntu-24.04-${{ runner.arch }}-release
source-dir: ${{ github.workspace }}/brlcad
output-dir: ${{ runner.temp }}/bext_output
build-type: Release
artifact-token: ${{ secrets.BEXT_ARTIFACT_TOKEN }}
- name: Directory setup
run: cmake -E make_directory build_distcheck-prepared_debug
- name: Configure
run: cmake -S brlcad -B build_distcheck-prepared_debug -G Ninja -DCMAKE_BUILD_TYPE=Debug -DBRLCAD_EXT_DIR=${{ runner.temp }}/bext_output
- name: Build
run: cmake --build build_distcheck-prepared_debug --config Debug --target distcheck-prepared_debug
- name: Log
if: always()
run: cat build_distcheck-prepared_debug/distcheck-prepared_debug.log
distcheck-prepared_release:
name: distcheck-prepared_release
runs-on: ubuntu-24.04
needs: [distcheck-no_unity_debug]
env:
DEBIAN_FRONTEND: noninteractive
if: ${{ !cancelled() && github.ref == 'refs/heads/main' }}
steps:
- name: Setup - CMake
uses: lukka/get-cmake@latest
- name: Install apt dependencies
run: |
sudo apt-get update
sudo apt-get install xserver-xorg-dev libx11-dev libxi-dev libxext-dev libglu1-mesa-dev libfontconfig-dev
sudo apt-get install astyle re2c
sudo apt-get install zlib1g-dev libpng-dev libjpeg-dev libtiff-dev libeigen3-dev libgdal-dev libassimp-dev libopencv-dev tcl-dev tk-dev libgl-dev libinput-dev
- name: Checkout
uses: actions/checkout@v6
with:
path: brlcad
- name: Prepare bext dependencies
uses: ./brlcad/.github/actions/prepare-bext
with:
platform-channel: ubuntu-24.04-${{ runner.arch }}-release
source-dir: ${{ github.workspace }}/brlcad
output-dir: ${{ runner.temp }}/bext_output
build-type: Release
artifact-token: ${{ secrets.BEXT_ARTIFACT_TOKEN }}
- name: Directory setup
run: cmake -E make_directory build_distcheck-prepared_release
- name: Configure
run: cmake -S brlcad -B build_distcheck-prepared_release -G Ninja -DCMAKE_BUILD_TYPE=Release -DBRLCAD_EXT_DIR=${{ runner.temp }}/bext_output
- name: Build
run: cmake --build build_distcheck-prepared_release --config Release --target distcheck-prepared_release
- name: Log
if: always()
run: cat build_distcheck-prepared_release/distcheck-prepared_release.log
distcheck-no_tcl:
name: distcheck-no_tcl
runs-on: ubuntu-24.04
needs: [distcheck-no_unity_release]
env:
DEBIAN_FRONTEND: noninteractive
if: ${{ !cancelled() && github.ref == 'refs/heads/main' }}
steps:
- name: Setup - CMake
uses: lukka/get-cmake@latest
- name: Install apt dependencies
run: |
sudo apt-get update
sudo apt-get install xserver-xorg-dev libx11-dev libxi-dev libxext-dev libglu1-mesa-dev libfontconfig-dev
sudo apt-get install astyle re2c
sudo apt-get install zlib1g-dev libpng-dev libjpeg-dev libtiff-dev libeigen3-dev libgdal-dev libassimp-dev libopencv-dev tcl-dev tk-dev libgl-dev libinput-dev
- name: Checkout
uses: actions/checkout@v6
with:
path: brlcad
- name: Prepare bext dependencies
uses: ./brlcad/.github/actions/prepare-bext
with:
platform-channel: ubuntu-24.04-${{ runner.arch }}-release
source-dir: ${{ github.workspace }}/brlcad
output-dir: ${{ runner.temp }}/bext_output
build-type: Release
artifact-token: ${{ secrets.BEXT_ARTIFACT_TOKEN }}
- name: Directory setup
run: cmake -E make_directory build_distcheck-no_tcl
- name: Configure
run: cmake -S brlcad -B build_distcheck-no_tcl -G Ninja -DCMAKE_BUILD_TYPE=Debug -DBRLCAD_EXT_DIR=${{ runner.temp }}/bext_output -DBRLCAD_ENABLE_TCL=OFF
- name: Build
run: cmake --build build_distcheck-no_tcl --config Debug --target distcheck-no_tcl
- name: Log
if: always()
run: cat build_distcheck-no_tcl/distcheck-no_tcl.log
distcheck-no_tk:
name: distcheck-no_tk
runs-on: ubuntu-24.04
needs: [distcheck-enableall_debug]
env:
DEBIAN_FRONTEND: noninteractive
if: ${{ !cancelled() && github.ref == 'refs/heads/main' }}
steps:
- name: Setup - CMake
uses: lukka/get-cmake@latest
- name: Install apt dependencies
run: |
sudo apt-get update
sudo apt-get install xserver-xorg-dev libx11-dev libxi-dev libxext-dev libglu1-mesa-dev libfontconfig-dev
sudo apt-get install astyle re2c
sudo apt-get install zlib1g-dev libpng-dev libjpeg-dev libtiff-dev libeigen3-dev libgdal-dev libassimp-dev libopencv-dev libgl-dev libinput-dev
- name: Checkout
uses: actions/checkout@v6
with:
path: brlcad
- name: Prepare bext dependencies
uses: ./brlcad/.github/actions/prepare-bext
with:
platform-channel: ubuntu-24.04-${{ runner.arch }}-release
source-dir: ${{ github.workspace }}/brlcad
output-dir: ${{ runner.temp }}/bext_output
build-type: Release
artifact-token: ${{ secrets.BEXT_ARTIFACT_TOKEN }}
- name: Directory setup
run: cmake -E make_directory build_distcheck-no_tk
- name: Configure
run: cmake -S brlcad -B build_distcheck-no_tk -G Ninja -DCMAKE_BUILD_TYPE=Debug -DBRLCAD_EXT_DIR=${{ runner.temp }}/bext_output -DBRLCAD_ENABLE_TK=OFF
- name: Build
run: cmake --build build_distcheck-no_tk --config Debug --target distcheck-no_tk
- name: Log
if: always()
run: cat build_distcheck-no_tk/distcheck-no_tk.log
distcheck-no_strict:
name: distcheck-no_strict
runs-on: ubuntu-24.04
needs: [distcheck-enableall_release]
env:
DEBIAN_FRONTEND: noninteractive
if: ${{ !cancelled() && github.ref == 'refs/heads/main' }}
steps:
- name: Setup - CMake
uses: lukka/get-cmake@latest
- name: Install apt dependencies
run: |
sudo apt-get update
sudo apt-get install xserver-xorg-dev libx11-dev libxi-dev libxext-dev libglu1-mesa-dev libfontconfig-dev
sudo apt-get install astyle re2c
sudo apt-get install zlib1g-dev libpng-dev libjpeg-dev libtiff-dev libeigen3-dev libgdal-dev libassimp-dev libopencv-dev tcl-dev tk-dev libgl-dev libinput-dev
- name: Checkout
uses: actions/checkout@v6
with:
path: brlcad
- name: Prepare bext dependencies
uses: ./brlcad/.github/actions/prepare-bext
with:
platform-channel: ubuntu-24.04-${{ runner.arch }}-release
source-dir: ${{ github.workspace }}/brlcad
output-dir: ${{ runner.temp }}/bext_output
build-type: Release
artifact-token: ${{ secrets.BEXT_ARTIFACT_TOKEN }}
- name: Directory setup
run: cmake -E make_directory build_distcheck-no_strict
- name: Configure
run: cmake -S brlcad -B build_distcheck-no_strict -G Ninja -DCMAKE_BUILD_TYPE=Debug -DBRLCAD_EXT_DIR=${{ runner.temp }}/bext_output -DBRLCAD_ENABLE_STRICT=OFF
- name: Build
run: cmake --build build_distcheck-no_strict --config Debug --target distcheck-no_strict
- name: Log
if: always()
run: cat build_distcheck-no_strict/distcheck-no_strict.log
distcheck-no_object:
name: distcheck-no_object
runs-on: ubuntu-24.04
needs: [distcheck-prepared_debug]
env:
DEBIAN_FRONTEND: noninteractive
if: ${{ !cancelled() && github.ref == 'refs/heads/main' }}
steps:
- name: Setup - CMake
uses: lukka/get-cmake@latest
- name: Install apt dependencies
run: |
sudo apt-get update
sudo apt-get install xserver-xorg-dev libx11-dev libxi-dev libxext-dev libglu1-mesa-dev libfontconfig-dev
sudo apt-get install astyle re2c
sudo apt-get install zlib1g-dev libpng-dev libjpeg-dev libtiff-dev libeigen3-dev libgdal-dev libassimp-dev libopencv-dev tcl-dev tk-dev libgl-dev libinput-dev
- name: Checkout
uses: actions/checkout@v6
with:
path: brlcad
- name: Prepare bext dependencies
uses: ./brlcad/.github/actions/prepare-bext
with:
platform-channel: ubuntu-24.04-${{ runner.arch }}-release
source-dir: ${{ github.workspace }}/brlcad
output-dir: ${{ runner.temp }}/bext_output
build-type: Release
artifact-token: ${{ secrets.BEXT_ARTIFACT_TOKEN }}
- name: Directory setup
run: cmake -E make_directory build_distcheck-no_object
- name: Configure
run: cmake -S brlcad -B build_distcheck-no_object -G Ninja -DCMAKE_BUILD_TYPE=Debug -DBRLCAD_EXT_DIR=${{ runner.temp }}/bext_output -DUSE_OBJECT_LIBS=OFF
- name: Build
run: cmake --build build_distcheck-no_object --config Debug --target distcheck-no_object
- name: Log
if: always()
run: cat build_distcheck-no_object/distcheck-no_object.log
distcheck-odd_pathnames:
name: distcheck-odd_pathnames
runs-on: ubuntu-24.04
needs: [distcheck-prepared_release]
env:
DEBIAN_FRONTEND: noninteractive
if: ${{ !cancelled() && github.ref == 'refs/heads/main' }}
steps:
- name: Setup - CMake
uses: lukka/get-cmake@latest
- name: Install apt dependencies
run: |
sudo apt-get update
sudo apt-get install xserver-xorg-dev libx11-dev libxi-dev libxext-dev libglu1-mesa-dev libfontconfig-dev
sudo apt-get install astyle re2c
sudo apt-get install zlib1g-dev libpng-dev libjpeg-dev libtiff-dev libeigen3-dev libgdal-dev libassimp-dev libopencv-dev tcl-dev tk-dev libgl-dev libinput-dev
- name: Checkout
uses: actions/checkout@v6
with:
path: brlcad
- name: Prepare bext dependencies
uses: ./brlcad/.github/actions/prepare-bext
with:
platform-channel: ubuntu-24.04-${{ runner.arch }}-release
source-dir: ${{ github.workspace }}/brlcad
output-dir: ${{ runner.temp }}/bext_output
build-type: Release
artifact-token: ${{ secrets.BEXT_ARTIFACT_TOKEN }}
- name: Directory setup
run: cmake -E make_directory build_distcheck-odd_pathnames
- name: Configure
run: cmake -S brlcad -B build_distcheck-odd_pathnames -G Ninja -DCMAKE_BUILD_TYPE=Debug -DBRLCAD_EXT_DIR=${{ runner.temp }}/bext_output
- name: Build
run: cmake --build build_distcheck-odd_pathnames --config Debug --target distcheck-odd_pathnames
- name: Log
if: always()
run: cat build_distcheck-odd_pathnames/distcheck-odd_pathnames.log
distcheck-in_src_dir:
name: distcheck-in_src_dir
runs-on: ubuntu-24.04
needs: [distcheck-no_tcl]
env:
DEBIAN_FRONTEND: noninteractive
if: ${{ !cancelled() && github.ref == 'refs/heads/main' }}
steps:
- name: Setup - CMake
uses: lukka/get-cmake@latest
- name: Install apt dependencies
run: |
sudo apt-get update
sudo apt-get install xserver-xorg-dev libx11-dev libxi-dev libxext-dev libglu1-mesa-dev libfontconfig-dev
sudo apt-get install astyle re2c
sudo apt-get install zlib1g-dev libpng-dev libjpeg-dev libtiff-dev libeigen3-dev libgdal-dev libassimp-dev libopencv-dev tcl-dev tk-dev libgl-dev libinput-dev
- name: Checkout
uses: actions/checkout@v6
with:
path: brlcad
- name: Prepare bext dependencies
uses: ./brlcad/.github/actions/prepare-bext
with:
platform-channel: ubuntu-24.04-${{ runner.arch }}-release
source-dir: ${{ github.workspace }}/brlcad
output-dir: ${{ runner.temp }}/bext_output
build-type: Release
artifact-token: ${{ secrets.BEXT_ARTIFACT_TOKEN }}
- name: Directory setup
run: cmake -E make_directory build_distcheck-in_src_dir
- name: Configure
run: cmake -S brlcad -B build_distcheck-in_src_dir -G Ninja -DCMAKE_BUILD_TYPE=Debug -DBRLCAD_EXT_DIR=${{ runner.temp }}/bext_output
- name: Build
run: cmake --build build_distcheck-in_src_dir --config Debug --target distcheck-in_src_dir
- name: Log
if: always()
run: cat build_distcheck-in_src_dir/distcheck-in_src_dir.log
-85
View File
@@ -1,85 +0,0 @@
# The purpose of this particular test definition is to support on-demand
# interactive command shells. We sometimes see problems that occur only in the
# Github Runner environments, and in order to explore what is happening we need
# an interactive prompt (the alternative is hours-per-cycle submit and test
# loops, which doesn't scale at all.)
#
# Unlike the other BRL-CAD tests, this one is started manually from the Github
# website. For more information see https://mxschmitt.github.io/action-tmate/
#
# The "recommended" way to use this action is for the dev to make a fork of
# the repository, alter the configure and/or build logic below for their
# particular use case (the example below is a libged-only build used to zero
# in on a specific libged behavior) before running.
name: BRL-CAD Linux Interactive Debugging
on:
workflow_dispatch:
inputs:
debug_enabled:
type: boolean
description: 'Run the build with tmate debugging enabled (https://github.com/marketplace/actions/debugging-with-tmate)'
required: false
default: false
jobs:
linux:
name: Ubuntu Latest GCC
runs-on: ubuntu-latest
steps:
- name: Setup - CMake
uses: lukka/get-cmake@latest
- name: Setup - System
env:
DEBIAN_FRONTEND: noninteractive
run: |
sudo apt-get update
# Install X/OpenGL dev pkgs
sudo apt-get install xserver-xorg-dev libx11-dev libxi-dev libxext-dev libglu1-mesa-dev libfontconfig-dev
# Install tools
sudo apt-get install astyle re2c xsltproc libxml2-utils liblief-dev
# Install dependency dev pkgs
sudo apt-get install zlib1g-dev libpng-dev libjpeg-dev libtiff-dev libeigen3-dev libgdal-dev libassimp-dev libopencv-dev tcl-dev tk-dev
# Cleanup (we want to avoid wasting disk space)
sudo apt-get clean
- name: Setup - System Qt Build Requirements
env:
DEBIAN_FRONTEND: noninteractive
run: |
sudo apt-get update
# Install XCB/OpenGL dev pkgs for Qt - see:
# https://wiki.qt.io/Building_Qt_6_from_Git
# https://doc.qt.io/qt-6/linux-requirements.html
sudo apt-get install libfontconfig1-dev libfreetype6-dev libx11-dev libx11-xcb-dev libxext-dev libxfixes-dev libxi-dev libxrender-dev libxcb1-dev libxcb-cursor-dev libxcb-glx0-dev libxcb-keysyms1-dev libxcb-image0-dev libxcb-shm0-dev libxcb-icccm4-dev libxcb-sync-dev libxcb-xfixes0-dev libxcb-shape0-dev libxcb-randr0-dev libxcb-render-util0-dev libxcb-util-dev libxcb-xinerama0-dev libxcb-xkb-dev libxkbcommon-dev libxkbcommon-x11-dev
sudo apt-get install libgl-dev
sudo apt-get install libinput-dev
sudo apt-get clean
- name: Checkout
uses: actions/checkout@v6
- name: Build Directory setup
run: |
cmake -E make_directory ./build_linux
- name: Configure
run: |
export PATH=$GITHUB_WORKSPACE:$PATH
cmake -S . -G Ninja -B build_linux -DBRLCAD_EXT_PARALLEL=1 -DBRLCAD_COMPONENTS=libged -DBRLCAD_EXTRADOCS=OFF
- name: Build
run: |
export PATH=$GITHUB_WORKSPACE:$PATH
cmake --build build_linux --config Release --target check
- name: Debugging - tmate session
if: ${{ github.event_name == 'workflow_dispatch' && inputs.debug_enabled }}
uses: mxschmitt/action-tmate@v3
with:
limit-access-to-actor: true
-449
View File
@@ -1,449 +0,0 @@
# This file defines Continuous Integration (CI) tests for BRL-CAD using the
# Github Actions framework that are executed each time a commit is pushed.
# Currently it defines configurations for Windows, Linux and OSX.
#
# For more information about available platforms for testing, see:
#
# https://docs.github.com/en/free-pro-team@latest/actions/reference/specifications-for-github-hosted-runners
#
# The general rule when building in CI is to go more verbose in output settings
# rather than less, since iterative debugging isn't practical. We also want to
# avoid parallel building - while that will sometimes catch dependency issues,
# it also makes the outputs far harder to interpret when there is a problem.
# Better to do parallel build debugging in an environment were more interactive
# and iterative debugging is available while preserving the readability of the
# CI outputs for other issues.
name: Per-push
on:
push:
jobs:
linux:
name: Ubuntu GCC
runs-on: ubuntu-24.04
strategy:
fail-fast: true
env:
DEBIAN_FRONTEND: noninteractive
if: github.event_name == 'push'
steps:
- name: Setup - CMake
uses: lukka/get-cmake@latest
# Install system dependencies
- name: Install apt dependencies
run: |
sudo apt-get update
# Install X/OpenGL dev pkgs
sudo apt-get install xserver-xorg-dev libx11-dev libxi-dev libxext-dev libglu1-mesa-dev libfontconfig-dev
# Install tools
sudo apt-get install astyle re2c xsltproc libxml2-utils
# Install dependency dev pkgs
sudo apt-get install zlib1g-dev libpng-dev libjpeg-dev libtiff-dev libeigen3-dev libgdal-dev libassimp-dev libopencv-dev tcl-dev tk-dev
# Install XCB/OpenGL dev pkgs for Qt - see:
# https://wiki.qt.io/Building_Qt_6_from_Git
# https://doc.qt.io/qt-6/linux-requirements.html
sudo apt-get install libfontconfig1-dev libfreetype6-dev libx11-dev libx11-xcb-dev libxext-dev libxfixes-dev libxi-dev libxrender-dev libxcb1-dev libxcb-cursor-dev libxcb-glx0-dev libxcb-keysyms1-dev libxcb-image0-dev libxcb-shm0-dev libxcb-icccm4-dev libxcb-sync-dev libxcb-xfixes0-dev libxcb-shape0-dev libxcb-randr0-dev libxcb-render-util0-dev libxcb-util-dev libxcb-xinerama0-dev libxcb-xkb-dev libxcb-xinput-dev libxcb-xrm-dev libxkbcommon-dev libxkbcommon-x11-dev
sudo apt-get install libgl-dev
sudo apt-get install libinput-dev
- name: Checkout
uses: actions/checkout@v6
with:
path: brlcad
- name: Prepare bext dependencies
uses: ./brlcad/.github/actions/prepare-bext
with:
platform-channel: ubuntu-24.04-${{ runner.arch }}-release
source-dir: ${{ github.workspace }}/brlcad
output-dir: ${{ runner.temp }}/bext_output
build-type: Release
artifact-token: ${{ secrets.BEXT_ARTIFACT_TOKEN }}
- name: Directory setup
run: |
cmake -E make_directory ./build_linux
cmake -E make_directory $HOME/.cache
cmake -E make_directory $HOME/.cache/BRL-CAD
- name: Configure
run: |
export PATH=$GITHUB_WORKSPACE:$PATH
cmake -S brlcad -B build_linux -G Ninja -DCMAKE_BUILD_TYPE=Release -DBRLCAD_EXT_DIR=${{ runner.temp }}/bext_output -DBRLCAD_ENABLE_QT=ON
- name: Build
id: build_parallel
run: |
export PATH=$GITHUB_WORKSPACE:$PATH
cmake --build build_linux --config Release --target check -j2
cmake --build build_linux --config Release --target package -j2
continue-on-error: true
- name: Build (serial for diagnostics)
if: steps.build_parallel.outcome == 'failure'
run: |
export PATH=$GITHUB_WORKSPACE:$PATH
cmake --build build_linux --config Release --target check
cmake --build build_linux --config Release --target package
# A full distcheck is too expensive for the runners, but we can run the
# repository integrity check and make sure we can build source archives.
archives:
name: Source Archives
runs-on: ubuntu-24.04
needs: [linux]
strategy:
fail-fast: true
env:
DEBIAN_FRONTEND: noninteractive
if: github.event_name == 'push'
steps:
- name: Setup - CMake
uses: lukka/get-cmake@latest
# Install system dependencies - we do the full setup here, even though
# source archives isn't intended to build the main BRL-CAD, in case
# this check is the one where the bext dependency cache check gets a miss.
# In that case, this check will have to build bext to proceed - and it will
# need the bext environment set up to do so.
- name: Install apt dependencies
run: |
sudo apt-get update
# Install X/OpenGL dev pkgs
sudo apt-get install xserver-xorg-dev libx11-dev libxi-dev libxext-dev libglu1-mesa-dev libfontconfig-dev
# Install tools
sudo apt-get install astyle re2c xsltproc libxml2-utils
# Install dependency dev pkgs
sudo apt-get install zlib1g-dev libpng-dev libjpeg-dev libtiff-dev libeigen3-dev libgdal-dev libassimp-dev libopencv-dev tcl-dev tk-dev
# Install XCB/OpenGL dev pkgs for Qt - see:
# https://wiki.qt.io/Building_Qt_6_from_Git
# https://doc.qt.io/qt-6/linux-requirements.html
sudo apt-get install libfontconfig1-dev libfreetype6-dev libx11-dev libx11-xcb-dev libxext-dev libxfixes-dev libxi-dev libxrender-dev libxcb1-dev libxcb-cursor-dev libxcb-glx0-dev libxcb-keysyms1-dev libxcb-image0-dev libxcb-shm0-dev libxcb-icccm4-dev libxcb-sync-dev libxcb-xfixes0-dev libxcb-shape0-dev libxcb-randr0-dev libxcb-render-util0-dev libxcb-util-dev libxcb-xinerama0-dev libxcb-xkb-dev libxcb-xinput-dev libxcb-xrm-dev libxkbcommon-dev libxkbcommon-x11-dev
sudo apt-get install libgl-dev
sudo apt-get install libinput-dev
- name: Checkout
uses: actions/checkout@v6
with:
path: brlcad
- name: Prepare bext dependencies
uses: ./brlcad/.github/actions/prepare-bext
with:
platform-channel: ubuntu-24.04-${{ runner.arch }}-release
source-dir: ${{ github.workspace }}/brlcad
output-dir: ${{ runner.temp }}/bext_output
build-type: Release
artifact-token: ${{ secrets.BEXT_ARTIFACT_TOKEN }}
- name: Build
run: |
cmake -E make_directory build_archives
cmake -S brlcad -B build_archives -DCMAKE_BUILD_TYPE=Release -DBRLCAD_EXT_PARALLEL=1 -DBRLCAD_EXT_DIR=${{ runner.temp }}/bext_output
cmake --build build_archives --config Release --target distcheck-source_archives
# A full bext build every time we push is too much, but we can exercise the
# basic bext mechanisms and also the BRLCAD_COMPONENTS subbuild at the same
# time if we do a local bext build of *just* the libbg subset of BRL-CAD. If
# the COMPONENTS mechanism works as it should it won't trigger a full bext
# build, and we'll only be compiling what libbg needs.
componentbext:
name: BRLCAD_COMPONENTS
runs-on: ubuntu-latest
strategy:
fail-fast: true
env:
DEBIAN_FRONTEND: noninteractive
if: github.event_name == 'push'
steps:
- name: Setup - CMake
uses: lukka/get-cmake@latest
# Install system dependencies - we do the full setup here, even though
# source archives isn't intended to build the main BRL-CAD, in case
# this check is the one where the bext dependency cache check gets a miss.
# In that case, this check will have to build bext to proceed - and it will
# need the bext environment set up to do so.
- name: Install apt dependencies
run: |
sudo apt-get update
# Install X/OpenGL dev pkgs
sudo apt-get install xserver-xorg-dev libx11-dev libxi-dev libxext-dev libglu1-mesa-dev libfontconfig-dev
# Install tools
sudo apt-get install astyle re2c xsltproc libxml2-utils
# Install dependency dev pkgs
sudo apt-get install zlib1g-dev libpng-dev libjpeg-dev libtiff-dev libeigen3-dev libgdal-dev libassimp-dev libopencv-dev tcl-dev tk-dev
# Install XCB/OpenGL dev pkgs for Qt - see:
# https://wiki.qt.io/Building_Qt_6_from_Git
# https://doc.qt.io/qt-6/linux-requirements.html
sudo apt-get install libfontconfig1-dev libfreetype6-dev libx11-dev libx11-xcb-dev libxext-dev libxfixes-dev libxi-dev libxrender-dev libxcb1-dev libxcb-cursor-dev libxcb-glx0-dev libxcb-keysyms1-dev libxcb-image0-dev libxcb-shm0-dev libxcb-icccm4-dev libxcb-sync-dev libxcb-xfixes0-dev libxcb-shape0-dev libxcb-randr0-dev libxcb-render-util0-dev libxcb-util-dev libxcb-xinerama0-dev libxcb-xkb-dev libxcb-xinput-dev libxcb-xrm-dev libxkbcommon-dev libxkbcommon-x11-dev
sudo apt-get install libgl-dev
sudo apt-get install libinput-dev
- name: Checkout
uses: actions/checkout@v6
with:
path: brlcad
- name: Directory setup
run: |
cmake -E make_directory build_components
cmake -E make_directory $HOME/.cache
cmake -E make_directory $HOME/.cache/BRL-CAD
- name: Build
run: |
cmake -S brlcad -B build_components -DCMAKE_BUILD_TYPE=Release -DBRLCAD_COMPONENTS=libbg
cmake --build build_components --config Release
windows:
name: MSVC - Ninja
runs-on: windows-2025
strategy:
fail-fast: true
if: github.event_name == 'push'
steps:
- name: Setup - CMake
uses: lukka/get-cmake@latest
- name: Add msbuild to PATH
uses: microsoft/setup-msbuild@v3
- name: Add cl.exe to PATH
uses: ilammy/msvc-dev-cmd@v1
- name: Add github workspace to path
shell: pwsh
run: Add-Content -Path $env:GITHUB_PATH -Value $env:GITHUB_WORKSPACE
- name: Checkout
uses: actions/checkout@v6
with:
path: brlcad
- name: Prepare bext dependencies
uses: ./brlcad/.github/actions/prepare-bext
with:
platform-channel: windows-2025-${{ runner.arch }}-release
source-dir: ${{ github.workspace }}/brlcad
output-dir: ${{ runner.temp }}/bext_output
build-type: Release
artifact-token: ${{ secrets.BEXT_ARTIFACT_TOKEN }}
- name: Build Directory setup
run: cmake -E make_directory ./build_winninja
- name: Configure
shell: powershell
run: |
cmake -S brlcad -B build_winninja -G Ninja -DCMAKE_C_COMPILER="cl.exe" -DCMAKE_CXX_COMPILER="cl.exe" -DBRLCAD_EXT_DIR=${{ runner.temp }}\bext_output -DCMAKE_BUILD_TYPE=Release -DBRLCAD_ENABLE_QT=ON
- name: Build
id: build_parallel
shell: powershell
run: |
ninja
working-directory: ${{ github.workspace }}/build_winninja
continue-on-error: true
- name: Build (serial for diagnostics)
if: steps.build_parallel.outcome == 'failure'
shell: powershell
run: |
ninja -j1 -v
working-directory: ${{ github.workspace }}/build_winninja
- name: Check
shell: powershell
run: |
ninja check -v
working-directory: ${{ github.workspace }}/build_winninja
- name: Package
shell: powershell
run: |
ninja package
working-directory: ${{ github.workspace }}/build_winninja
windows_std_tools:
name: MSVC - Standard Tools
needs: [windows]
runs-on: windows-2025
strategy:
fail-fast: true
if: github.event_name == 'push'
steps:
- name: Setup - CMake
uses: lukka/get-cmake@latest
- name: Add msbuild to PATH
uses: microsoft/setup-msbuild@v3
- name: Add cl.exe to PATH
uses: ilammy/msvc-dev-cmd@v1
- name: Checkout
uses: actions/checkout@v6
with:
path: brlcad
- name: Prepare bext dependencies
uses: ./brlcad/.github/actions/prepare-bext
with:
platform-channel: windows-2025-${{ runner.arch }}-release
source-dir: ${{ github.workspace }}/brlcad
output-dir: ${{ runner.temp }}/bext_output
build-type: Release
artifact-token: ${{ secrets.BEXT_ARTIFACT_TOKEN }}
- name: Build Directory setup
run: |
cmake -E make_directory ./build_winstd
- name: MSVC and Ninja diagnostics
shell: cmd
run: |
where cmake
where ninja
where cl.exe
where msbuild
cmake --version
cl.exe
set INCLUDE
set LIB
set LIBPATH
- name: Configure
shell: cmd
run: |
cmake -S brlcad -B build_winstd -DBRLCAD_EXT_PARALLEL=1 -DBRLCAD_BUNDLED_LIBS=Bundled -DCMAKE_BUILD_TYPE=Release -DBRLCAD_EXT_DIR=%RUNNER_TEMP%\bext_output -DBRLCAD_ENABLE_QT=ON -DBRLCAD_CONFIG_PROBE_DIAGNOSTICS=ON -DBRLCAD_PROBE_SNAPSHOT_FILE=%GITHUB_WORKSPACE%\build_winstd\parallel-probes.txt
- name: Configure probe diagnostics
if: always()
shell: pwsh
run: |
$build = Join-Path $env:GITHUB_WORKSPACE 'build_winstd'
$diagnosticDir = Join-Path $build 'CMakeTmp/probe_diagnostics'
if (Test-Path $diagnosticDir) {
Get-ChildItem -Path $diagnosticDir -File | Sort-Object Name | ForEach-Object {
Write-Host "`n===== $($_.FullName) ====="
Get-Content -Path $_.FullName
}
} else {
Write-Host "No parallel-probe diagnostic directory was created."
}
$cmakeError = Join-Path $build 'CMakeFiles/CMakeError.log'
if (Test-Path $cmakeError) {
Write-Host "`n===== $cmakeError ====="
Get-Content -Path $cmakeError
}
$cache = Join-Path $build 'CMakeCache.txt'
if (Test-Path $cache) {
Write-Host "`n===== selected cache entries ====="
Select-String -Path $cache -Pattern '^(HAVE_CONIO_H|BRLCAD_PROBE_USE_NINJA|BRLCAD_PROBE_NINJA_EXE|BRLCAD_PROBE_VCVARS|BRLCAD_PROBE_VCVARS_ARCH):' | ForEach-Object { $_.Line }
}
- name: Rebuild conio probe verbosely
if: always()
shell: cmd
continue-on-error: true
run: |
if not exist build_winstd\CMakeTmp\INCLUDE_PROBE_build (
echo INCLUDE_PROBE mini-project was not configured.
exit /b 0
)
cmake --build build_winstd\CMakeTmp\INCLUDE_PROBE_build --config Release --target HAVE_CONIO_H --verbose
- name: Build
id: build_parallel
shell: cmd
run: |
cmake --build build_winstd --config Release -j2
continue-on-error: true
- name: Build (serial for diagnostics)
if: steps.build_parallel.outcome == 'failure'
shell: cmd
run: |
cmake --build build_winstd --config Release --target mged
- name: Check
shell: cmd
run: |
cmake --build build_winstd --config Release --target check -j2
- name: Package
shell: cmd
run: |
cmake --build build_winstd --config Release --target package -j2
osx:
name: macOS Clang
needs: [linux]
runs-on: macos-14
strategy:
fail-fast: true
steps:
- name: Setup - CMake
uses: lukka/get-cmake@latest
- name: Install Xquartz
run: |
brew install xquartz --cask
- name: Checkout
uses: actions/checkout@v6
with:
path: brlcad
- name: Prepare bext dependencies
uses: ./brlcad/.github/actions/prepare-bext
with:
platform-channel: macos-14-${{ runner.arch }}-release
source-dir: ${{ github.workspace }}/brlcad
output-dir: ${{ runner.temp }}/bext_output
build-type: Release
artifact-token: ${{ secrets.BEXT_ARTIFACT_TOKEN }}
- name: Build Directory setup
run: |
cmake -E make_directory build_osx
cmake -E make_directory $HOME/.cache
cmake -E make_directory $HOME/.cache/BRL-CAD
- name: Configure
run: |
export PATH=$GITHUB_WORKSPACE:$PATH
export CC=clang
export CXX=clang++
cmake -S brlcad -B build_osx -DCMAKE_BUILD_TYPE=Release -DBRLCAD_EXT_DIR=${{ runner.temp }}/bext_output -DBRLCAD_ENABLE_QT=ON
- name: Build
id: build_parallel
run: |
export PATH=$GITHUB_WORKSPACE:$PATH
make -j2
working-directory: ${{ github.workspace }}/build_osx
continue-on-error: true
- name: Build (serial for diagnostics)
if: steps.build_parallel.outcome == 'failure'
run: |
make
working-directory: ${{ github.workspace }}/build_osx
- name: Check
run: |
export PATH=$GITHUB_WORKSPACE:$PATH
make check
working-directory: ${{ github.workspace }}/build_osx
- name: Package
run: |
export PATH=$GITHUB_WORKSPACE:$PATH
make package
working-directory: ${{ github.workspace }}/build_osx
-400
View File
@@ -1,400 +0,0 @@
# This file defines Continuous Integration (CI) tests for BRL-CAD using the
# Github Actions framework. Currently it defines configurations for Windows,
# Linux and OSX. These tests are run on a fixed schedule, rather than per
# push, and will typically take longer to run.
#
# Tests here are intended to test more expensive integrations and longer
# builds than the ones targeted at per-commit feedback. The tradeoff is
# that a failure in these tests might be cause by any commit within a
# 24 hour block of time, so the developer will need to track down the
# specifics themselves.
name: Scheduled
on:
schedule:
- cron: '0 3 * * *' # daily at 03:00 UTC
workflow_dispatch:
jobs:
linux_bext:
name: Linux - BRL-CAD bext build
runs-on: ubuntu-latest
strategy:
fail-fast: true
env:
DEBIAN_FRONTEND: noninteractive
steps:
- name: Setup - CMake
uses: lukka/get-cmake@latest
# Install system dependencies
- name: Install apt dependencies
run: |
sudo apt-get update
# Install X/OpenGL dev pkgs
sudo apt-get install xserver-xorg-dev libx11-dev libxi-dev libxext-dev libglu1-mesa-dev libfontconfig-dev
# Install tools
sudo apt-get install astyle re2c xsltproc libxml2-utils
# Install dependency dev pkgs
sudo apt-get install zlib1g-dev libpng-dev libjpeg-dev libtiff-dev libeigen3-dev libgdal-dev libassimp-dev libopencv-dev tcl-dev tk-dev
# Install XCB/OpenGL dev pkgs for Qt - see:
# https://wiki.qt.io/Building_Qt_6_from_Git
# https://doc.qt.io/qt-6/linux-requirements.html
sudo apt-get install libfontconfig1-dev libfreetype6-dev libx11-dev libx11-xcb-dev libxext-dev libxfixes-dev libxi-dev libxrender-dev libxcb1-dev libxcb-cursor-dev libxcb-glx0-dev libxcb-keysyms1-dev libxcb-image0-dev libxcb-shm0-dev libxcb-icccm4-dev libxcb-sync-dev libxcb-xfixes0-dev libxcb-shape0-dev libxcb-randr0-dev libxcb-render-util0-dev libxcb-util-dev libxcb-xinerama0-dev libxcb-xkb-dev libxcb-xinput-dev libxcb-xrm-dev libxkbcommon-dev libxkbcommon-x11-dev
sudo apt-get install libgl-dev
sudo apt-get install libinput-dev
- name: Checkout
uses: actions/checkout@v6
with:
path: brlcad
- name: Directory setup
run: |
cmake -E make_directory build_linux
cmake -E make_directory $HOME/.cache
cmake -E make_directory $HOME/.cache/BRL-CAD
- name: Configure
run: |
export PATH=$GITHUB_WORKSPACE:$PATH
cmake -S brlcad -B build_linux -G Ninja -DCMAKE_BUILD_TYPE=Release -DBRLCAD_EXT_PARALLEL=1 -DBRLCAD_BEXT_CLEANUP=ON -DBRLCAD_ENABLE_QT=ON
- name: Build + Check + Package
run: |
export PATH=$GITHUB_WORKSPACE:$PATH
cmake --build build_linux --config Release --target check
cmake --build build_linux --config Release --target package
windows_bext:
name: MSVC - Ninja - BRL-CAD bext build
needs: [linux_bext]
runs-on: windows-latest
strategy:
fail-fast: true
if: ${{ !cancelled() }}
steps:
- name: Setup - CMake
uses: lukka/get-cmake@latest
- name: Add msbuild to PATH
uses: microsoft/setup-msbuild@v3
- name: Add cl.exe to PATH
uses: ilammy/msvc-dev-cmd@v1
- name: Add github workspace to path
shell: powershell
run: Add-Content -Path $env:GITHUB_PATH -Value $env:GITHUB_WORKSPACE
- name: Checkout
uses: actions/checkout@v6
with:
path: brlcad
- name: Build Directory setup
run: cmake -E make_directory ./build_winninja
- name: Configure
shell: powershell
run: |
cmake -S brlcad -B build_winninja -G Ninja -DCMAKE_C_COMPILER="cl.exe" -DCMAKE_CXX_COMPILER="cl.exe" -DCMAKE_BUILD_TYPE=Release -DBRLCAD_EXT_PARALLEL=1 -DBRLCAD_BEXT_CLEANUP=ON -DBRLCAD_ENABLE_QT=ON
- name: Build
shell: powershell
run: |
ninja -j1 -v
working-directory: ${{ github.workspace }}/build_winninja
- name: Check
shell: powershell
run: |
ninja check -v
working-directory: ${{ github.workspace }}/build_winninja
- name: Package
shell: powershell
run: |
ninja package
working-directory: ${{ github.workspace }}/build_winninja
windows_std_tools_bext:
name: MSVC - Standard Tools - BRL-CAD bext build
needs: [windows_bext]
runs-on: windows-latest
strategy:
fail-fast: true
if: ${{ !cancelled() }}
steps:
- name: Setup - CMake
uses: lukka/get-cmake@latest
- name: Add msbuild to PATH
uses: microsoft/setup-msbuild@v3
- name: Add cl.exe to PATH
uses: ilammy/msvc-dev-cmd@v1
- name: Add github workspace to path
shell: cmd
run: echo %GITHUB_WORKSPACE%>>"%GITHUB_PATH%"
- name: Checkout
uses: actions/checkout@v6
with:
path: brlcad
- name: Build Directory setup
run: |
cmake -E make_directory ./build_winstd
- name: Configure
shell: cmd
run: |
where cmake
where ninja
where cl.exe
where msbuild
cmake -S brlcad -B build_winstd -DBRLCAD_EXT_PARALLEL=1 -DBRLCAD_BUNDLED_LIBS=Bundled -DCMAKE_BUILD_TYPE=Release -DBRLCAD_BEXT_CLEANUP=ON -DBRLCAD_ENABLE_QT=ON
- name: Build
shell: cmd
run: |
cmake --build build_winstd --config Release --target mged
- name: Check
shell: cmd
run: |
cmake --build build_winstd --config Release --target check
- name: Package
shell: cmd
run: |
cmake --build build_winstd --config Release --target package
osx_bext:
name: macOS - BRL-CAD bext build
needs: [linux_bext]
runs-on: macos-14
strategy:
fail-fast: true
if: ${{ !cancelled() }}
steps:
- name: Setup - CMake
uses: lukka/get-cmake@latest
- name: Install Xquartz
run: |
brew install xquartz --cask
- name: Checkout
uses: actions/checkout@v6
with:
path: brlcad
- name: Build Directory setup
run: |
cmake -E make_directory build_osx
cmake -E make_directory $HOME/.cache
cmake -E make_directory $HOME/.cache/BRL-CAD
- name: Configure
run: |
export PATH=$GITHUB_WORKSPACE:$PATH
export CC=clang
export CXX=clang++
cmake -S brlcad -B build_osx -DCMAKE_BUILD_TYPE=Release -DBRLCAD_EXT_PARALLEL=1 -DBRLCAD_BEXT_CLEANUP=ON -DBRLCAD_ENABLE_QT=ON
- name: Build
run: |
make
working-directory: ${{ github.workspace }}/build_osx
- name: Check
run: |
make check
working-directory: ${{ github.workspace }}/build_osx
- name: Package
run: |
make package
working-directory: ${{ github.workspace }}/build_osx
linux_static:
name: Clang Static Analyser
needs: [linux_bext]
runs-on: ubuntu-24.04
strategy:
fail-fast: true
env:
DEBIAN_FRONTEND: noninteractive
if: ${{ !cancelled() && github.ref == 'refs/heads/main' }}
steps:
- name: Setup - CMake
uses: lukka/get-cmake@latest
# Setup hint from https://github.com/darktable-org/rawspeed/blob/develop/.github/workflows/ci-static-analysis.yml
- name: Clang Static Analyzer Setup
run: |
sudo apt-get update
sudo apt-get install clang-18 clang-tools-18
# Install X/OpenGL dev pkgs
sudo apt-get install xserver-xorg-dev libx11-dev libxi-dev libxext-dev libglu1-mesa-dev libfontconfig-dev
# Install tools
sudo apt-get install astyle re2c xsltproc libxml2-utils
# Install dependency dev pkgs
sudo apt-get install zlib1g-dev libpng-dev libjpeg-dev libtiff-dev libeigen3-dev libgdal-dev libassimp-dev libopencv-dev tcl-dev tk-dev
# Install XCB/OpenGL dev pkgs for Qt - see:
# https://wiki.qt.io/Building_Qt_6_from_Git
# https://doc.qt.io/qt-6/linux-requirements.html
sudo apt-get install libfontconfig1-dev libfreetype6-dev libx11-dev libx11-xcb-dev libxext-dev libxfixes-dev libxi-dev libxrender-dev libxcb1-dev libxcb-cursor-dev libxcb-glx0-dev libxcb-keysyms1-dev libxcb-image0-dev libxcb-shm0-dev libxcb-icccm4-dev libxcb-sync-dev libxcb-xfixes0-dev libxcb-shape0-dev libxcb-randr0-dev libxcb-render-util0-dev libxcb-util-dev libxcb-xinerama0-dev libxcb-xkb-dev libxcb-xinput-dev libxcb-xrm-dev libxkbcommon-dev libxkbcommon-x11-dev
sudo apt-get install libgl-dev
sudo apt-get install libinput-dev # Cleanup
- name: Checkout
uses: actions/checkout@v6
with:
path: brlcad
- name: Prepare bext dependencies
uses: ./brlcad/.github/actions/prepare-bext
with:
platform-channel: ubuntu-24.04-${{ runner.arch }}-release
source-dir: ${{ github.workspace }}/brlcad
output-dir: ${{ runner.temp }}/bext_output
build-type: Release
artifact-token: ${{ secrets.BEXT_ARTIFACT_TOKEN }}
- name: Directory setup
run: |
cmake -E make_directory build_clangstatic
cmake -E make_directory $HOME/.cache
cmake -E make_directory $HOME/.cache/BRL-CAD
working-directory: ${{ github.workspace }}/brlcad
- name: Run Analyzer
env:
BRLCAD_EXT_DIR: ${{ runner.temp }}/bext_output
run: |
export PATH=$GITHUB_WORKSPACE:/usr/share/clang/scan-build-18/bin:/usr/share/clang/scan-build-18/libexec:$PATH
cp $GITHUB_WORKSPACE/brlcad/misc/clang-static-analyzer-run.sh .
./clang-static-analyzer-run.sh
working-directory: ${{ github.workspace }}/brlcad/build_clangstatic
- name: Summary
if: success() || failure()
run: |
sudo apt-get install html2text
html2text scan-reports-all/*/index.html
working-directory: ${{ github.workspace }}/brlcad/build_clangstatic
# See https://app.codecov.io/gh/BRL-CAD/brlcad for analysis results
linux_cov:
name: LCOV Coverage testing
needs: [linux_bext]
runs-on: ubuntu-24.04
strategy:
fail-fast: true
env:
DEBIAN_FRONTEND: noninteractive
if: ${{ !cancelled() && github.ref == 'refs/heads/main' }}
steps:
- name: Setup - CMake
uses: lukka/get-cmake@latest
- name: Setup - System
run: |
sudo apt-get update
# Get the lcov tool and its dependencies
sudo apt-get install lcov gdb
# Install X/OpenGL dev pkgs
sudo apt-get install xserver-xorg-dev libx11-dev libxi-dev libxext-dev libglu1-mesa-dev libfontconfig-dev
# Install tools
sudo apt-get install astyle re2c xsltproc libxml2-utils
# Install dependency dev pkgs
sudo apt-get install zlib1g-dev libpng-dev libjpeg-dev libtiff-dev libeigen3-dev libgdal-dev libassimp-dev libopencv-dev tcl-dev tk-dev
# Install XCB/OpenGL dev pkgs for Qt - see:
# https://wiki.qt.io/Building_Qt_6_from_Git
# https://doc.qt.io/qt-6/linux-requirements.html
sudo apt-get install libfontconfig1-dev libfreetype6-dev libx11-dev libx11-xcb-dev libxext-dev libxfixes-dev libxi-dev libxrender-dev libxcb1-dev libxcb-cursor-dev libxcb-glx0-dev libxcb-keysyms1-dev libxcb-image0-dev libxcb-shm0-dev libxcb-icccm4-dev libxcb-sync-dev libxcb-xfixes0-dev libxcb-shape0-dev libxcb-randr0-dev libxcb-render-util0-dev libxcb-util-dev libxcb-xinerama0-dev libxcb-xkb-dev libxcb-xinput-dev libxcb-xrm-dev libxkbcommon-dev libxkbcommon-x11-dev
sudo apt-get install libgl-dev
sudo apt-get install libinput-dev
- name: Checkout
uses: actions/checkout@v6
with:
path: brlcad
- name: Prepare bext dependencies
uses: ./brlcad/.github/actions/prepare-bext
with:
platform-channel: ubuntu-24.04-${{ runner.arch }}-release
source-dir: ${{ github.workspace }}/brlcad
output-dir: ${{ runner.temp }}/bext_output
build-type: Release
artifact-token: ${{ secrets.BEXT_ARTIFACT_TOKEN }}
- name: Directory setup
run: |
cmake -E make_directory build_lcov
cmake -E make_directory $HOME/.cache
cmake -E make_directory $HOME/.cache/BRL-CAD
- name: Configure
run: |
export PATH=$GITHUB_WORKSPACE:$PATH
cmake -S brlcad -B build_lcov -DBRLCAD_ENABLE_COVERAGE=ON -DCMAKE_BUILD_TYPE=Debug -DBRLCAD_EXT_DIR=${{ runner.temp }}/bext_output -DBRLCAD_ENABLE_QT=ON
- name: Build
id: build_parallel
run: |
export PATH=$GITHUB_WORKSPACE:$PATH
cmake --build build_lcov -j2
continue-on-error: true
- name: Build (serial for diagnostics)
if: steps.build_parallel.outcome == 'failure'
run: |
export PATH=$GITHUB_WORKSPACE:$PATH
cmake --build build_lcov -j1
- name: Run Tests
id: coverage_tests
run: |
find . -name '*.gcda' -exec rm {} \;
cmake --build . --target check
working-directory: ${{ github.workspace }}/build_lcov
- name: Diagnose failed annotation test
if: failure() && steps.coverage_tests.outcome == 'failure'
continue-on-error: true
run: |
set +e
ctest -R '^rt_datum_annot_semantics$' -VV
cat Testing/Temporary/LastTest.log
if command -v gdb >/dev/null 2>&1; then
gdb --quiet --batch \
-ex 'set pagination off' \
-ex run \
-ex 'thread apply all bt full' \
--args ./src/librt/tests/rt_datum_annot_semantics
fi
working-directory: ${{ github.workspace }}/build_lcov
- name: Capture Coverage
run: |
lcov --capture --directory . --output-file coverage.info
lcov -r coverage.info \*\/bext_output\/\* > coverage-2.info
lcov -r coverage-2.info \/usr\/\* > coverage_cad.info
rm coverage-*.info
mv coverage_cad.info ..
working-directory: ${{ github.workspace }}/build_lcov
- name: Upload
uses: codecov/codecov-action@v4
with:
files: ./coverage_cad.info
+32 -40
View File
@@ -1,41 +1,33 @@
# Common build directories used in the source tree
/build*
/.build*
/*_build*
/*-build*
/out
# Temporary files
# CVS default ignores begin
tags
TAGS
.make.state
.nse_depinfo
*~
\#*\#
.\#*
[._]*.s[a-v][a-z]
[._]*.sw[a-p]
[._]s[a-v][a-z]
[._]sw[a-p]
# OS specific files
.DS_Store
.DS_Store?
# CMake supports some configuration files to allow users a convenient way to pre-define
# sets of configuration options:
# https://cmake.org/cmake/help/latest/manual/cmake-presets.7.html
/CMakeUserPresets.json
# Visual Studio (note that CMakePresets.json is recommended instead of
# CMakeSettings.json for Visual Studio going forward)
# https://learn.microsoft.com/en-us/cpp/build/cmake-presets-vs
# https://learn.microsoft.com/en-us/cpp/build/customize-cmake-settings
/.vs
.vscode
/CMakeSettings.json
#Qt Creator
CMakeLists.txt.user
# Misc
.clang-format
*__pycache__*
\#*
.#*
,*
_$*
*$
*.old
*.bak
*.BAK
*.orig
*.rej
.del-*
*.a
*.olb
*.o
*.obj
*.so
*.exe
*.Z
*.elc
*.ln
core
# CVS default ignores end
.lib*.* .proc-db.* .cvsignore .util.* .patch.* .burst.* .iges.* .mged.*
.fbserv.* .canon.* .anim.* .bench.* .conv.* .remrt.* .tools.* .comgeom-g.*
.tab.* .sig.* .irprep.* .vdeck.* .fbed.* .jack.* .vas4.* .off.* .jove.*
.lgt.* .nirt.* .mk.* .db.* .fb.* .rt.* .halftone.* .gtools.*
.cake*.* .bwish.* .cwish.* .tk.* .btclsh.* .iwidgets* .unigraphics.*
-32
View File
@@ -1,32 +0,0 @@
# Code Quality Standards
Write code as a senior engineer would for long-term maintenance. These are non-negotiable defaults, not suggestions to apply when asked.
## Principles
- **DRY.** Extract duplicate logic. Refactor. Once and only once.
- **Minimize surprises.** Preserve existing style and conventions. Test when you can.
- **No magic values.** Use named constants, enums, or configuration. Every literal needs justification.
- **Minimize scope.** Prefer tightest scope that works - local variables, parameters, encapsulation. Broader scope needs justification.
- **No dead code.** Delete commented-out code, unused variables, unreachable branches. Version control remembers.
- **Comments explain why.** Document intent, constraints, and non-obvious decisions. Use "what" summaries only for complex or non-obvious algorithms. If routine code needs a comment to explain it, the code should be clearer.
- **Clean up what you touch.** Improve code you are changing: rename unclear variables, extract functions, simplify conditionals. Do not mix unrelated cleanup with logic changes - separate concerns, separate commits.
- **Handle errors deliberately.** Whether failing loudly or quietly, make it an intentional choice. No accidental swallowing.
- **YAGNI.** Do not add speculative abstractions, unused parameters, or unplanned extension points. Build what is needed now. Refactor when requirements actually change.
- **Perfection is when there is nothing left to take away.** Prefer reduction over addition, simpler is better. Too clever to debug easily is too clever.
## Before Finishing
Review your changes for code smells, duplicated logic, hardcoded values, overly broad scope, unclear names, missing error handling, unnecessary complexity, etc. Fix issues in the same pass - do not defer cleanup.
## Git
Never commit without permission (ask every time). Never push to remote. Never use `codex`, `chatgpt`, `openai`, `gemini`, `antigravity`, `copilot`, `claude`, `llm`, `ai`, or similar terms in branch names, tag names, commits, PRs, comments, and other metadata. Do not add generated-by notices or otherwise indicate authorship unless user explicitly requests. Do not include specific machine information - full file system paths, machine names, IP addresses, or other identifiable information in commit messages, code, comments or documentation.
## Repository Coding Conventions
The HACKING file in the root of the source tree defines coding conventions specific to BRL-CAD, including versions of common functions that are used in our code base instead of raw standard functions. Review this file before writing code so your changes and additions adhere to BRL-CAD standards.
BRL-CAD code should typically use our ZERO and EQUAL macros rather than raw floating-point equality comparisons to avoid Werror=float-equal compilation failures on expressions such as a == 0.0 (should be ZERO(a)) or b != c (should be !EQUAL(b, c)).
When completing a code change (not for intermediate iterations, but when preparing to hand back a finalized change) use our regress-repository and regress-licenses build targets to check that the result satisfies our internal checkers.
-1501
View File
File diff suppressed because it is too large Load Diff
+65
View File
@@ -0,0 +1,65 @@
The US Army BRL-CAD Develoment Team would like to take this opportunity
to thank the many people and organizations who have contributed code or
suggestions for improving the BRL-CAD Package:
Sun Microsystems (William C. Lindemann)
mged/dm-sun.c
Sun Microsystems (Timothy G. Smith, Christopher J. Jackson, and James D. Fiori)
Substantial fixes to ease Solaris 2.X porting
24-bit LIBFB support
New improved XGL support for Solaris
University of Alabama in Huntsville
Research Institute, RI E-47
Sparkman DR NW
Huntsville, AL 35899
POC: Mark Huston Bowden or M. Shane Strickland
mged/hideline.c Hidden line removal
mged/dm-hp.c HP2397A terminal
mged/m-ps390.c color version for serial line connection
mged/dm-pss.c gsr routines
util/pl-hpgl.c convert UNIX-plot file to HP plotter language
Geometric Solutions, Inc (Christopher T. Johnson) <cjohnson@camelot.com>
Paladin Software
Cray Research, Inc.
halftone/*
remrt/rtsrv control support, movie speed ups, extra commands
A/UX support
mged push support, articulation support, animation support
located awf for brlman support.
some plotting tools
bug fixes
too many dinner time bug reports
format converter support (librt/cv_* routines), CV program
scriptsort
Geometric Solutions: reed@camelot.com (Harry J. Reed)
havoc.g
tank-car.g
t62a.g
Manchester-Computing-Centre, UK (Terry Hewitt)
Computer Graphics Unit, MCC" <HEWITT@vmsfe.mcc.ac.uk>
and
Mario Brand <mgbk1@tnofel.fel.tno.nl>
Support for BRL-CAD on HP-9000/730:
machinetype.sh, Cakefile.defs, libplot3/htond.c
Bill Laut (Gull Island Consultants, Inc.)
P.O. Box 627, Muskegon, MI 49440
rt/sh_marble.c -- substantial enhancements
rt/sh_wood.c -- a completely new shader
h/light.h enhancements
rt/sh_light.c enhancements for more easily aimable lights.
Henry Spencer
Regular expression library
John Ousterhout <john.ousterhout@eng.sun.com>
Tcl/Tk
File diff suppressed because it is too large Load Diff
-621
View File
@@ -1,621 +0,0 @@
BRL-CAD Bugs
============
Bugs should be reported to the bug tracker on the project website at
http://sourceforge.net/tracker/?atid=640802&group_id=105292
The bugs and issues listed in here may or may not be the same as or
related to the bugs reported to the bug tracker. In general, users
should not look to this file for information regarding the status of
bugs. Informal bug-related information that is intended for
developers will generally be found here. This may include short term
issues that are in active development as well as long term and
on-going issues.
Recent Bugs
-----------
* fbserv as well as -F option handling (e.g., -F0 or -F/dev/wgls) that
is supported across myriad other tools appears to be broken on
Windows in a git bash shell (problem is not seen in Command Prompt.)
Something is concatenating EXEPATH and/or fbserv silently fails with
return codes (e.g., when not specifying -F, only giving the port.)
* recursive bu_parallel() failure, tbd whether cpp11 or pthread impl,
likely because IDs are exceeding MAX_PSW, causing mayhem and chaos.
* rtcheck_handler_cleanup() throws 'invalid handle specified' on Windows
in closing of STDOUT (see FIXME comment). Does not affect normal running,
but a debug build complains.
* very peculiar non-linear memory issue in rt when allocating a large
flat hierarchy of objects. I have three combs, each with 10k
members unioned. Each member is an rcc. Rendering with just one
comb results in about 2GB usage. Two combs result in about 3.5GB
usage. Three combs results in 18GB usage. Four is killed after
24GB. Suspect there is some 32-bit issue once we exceed 4GB that is
causing subsequent allocations to be bigger than necessary. Looking
at allocation stack, rt_ct_get() appears to be allocating 10MB
chunks.
[HARD] Superlinear growth (3 combs -> 18GB) points at an
integer/overflow interaction deep in the space-partitioning cut
allocator (rt_ct_get 10MB chunks), intertwined with bu memory.
Painful to isolate and validate at scale.
[FAN-OUT: poor -- one focused investigator with an allocator/profiler
trace; not parallelizable.]
* rt from mged is not outputting overlap log messages or rt summary.
Stops printing after opendb line. (Observed on Mac)
* mged running an rt with excessive overlaps ends up in a deadlock.
Backtrace indicates write buffer is full, likely because no output
is going to terminal. (Observed on Mac)
* Running"mged -c test.g" exits automatically on default prompt:
...
Create new database (y|n)[n]?
Warning: no database is currently open!
morrison@Miniagua .build %
* MGED crashes trying to open the repository file
doc/docbook/resources/other/standard/xsl/images/important.tif
It is mis-identified as a v4 .g file due to the file header's
first character matching the v4 .g first character.
* MGED on Mac hides the main command window on File->Open when you
cancel the open. Presumably the withdraw is somehow getting routed
to the window and not just the open dialog.
* running pkgIndex and/or mkIndex during build appears to be randomly
crashing on Mac using bundled libs
* Visual error when drawing using -S -m1 of a region with the same solid
subtracted and then unioned.
make two boxes stacked on top of one another
> r boxes.r u box - box1 u box1
> e -S -m1 boxes.r
box1 is not drawn
* raytracing a revolved sketch seems to work fine, but rtarea and gqa
seem to be crashing on that same revolve. curiously, the brep
revolve from the csgbrep proc-db has the same failure as well as the
brep ehy.
* ogl display manager still crashes on attach in mged on Mac OS X 10.5
* running archer "" at least on windows results in a file type dialog
and errors with "can't read "_conv_log": no such variable
* in mged, running the 'attach' command (confirmed issues with X and
ogl), closing the window, and then issuing a 'draw' results in mged
crashing.
* killtree / crashes
* object names with a / or \ in them make ls or underlying directory
parsing logic display them incorrectly.
* search -exec results are inconsistent with search filtered
results. for example, "search . -attr ..." returns A B C, but
"search . -attr ... -exec attr show {} \;" results in attr show
output for A B C as well as subtracted repetitions. For example,
say A contains - B - C, then it will show output for A B C B C.
adding -bool u gets closer to consistent but still appears to repeat
the last object
* fbclear -c appears to hang indefinitely inside pkg_bwaitfor,
possible protocol mismatch or capability removed/changed in fbserv.
* apparently all four BRL-CAD Tutorial Series volumes are missing from
our bibliography...
* mater -d information stored in the .g file doesn't survive a
garbage collection operation.
* fix checker.sh script and/or overlap GUI so that the latter will
read the resulting overlap pairings file from the prior.
alternatively, need to be able to run overlap check on server
without GUI, so could implement an overlaps file output option to be
run via mged -c.
* running 'put' on geometry that is already displayed results in a NaN
view (at least View and Eye_pos parameters are non) despite geometry
still being displayed. this causes 'rt' to fly into an infinite
loop, presumably trying to increment rays from the eye position.
* creating an object with a slashes in the name (e.g., cp foo foo/R)
results in an object that cannot be deleted/renamed. bad behavior
presumably extends to any name with path separators.
* If we draw any form, then trace it using rt, then change of database
(by clicking file>open and selecting another database), badness
ensues. One report has quitting the rt window causing a segfault.
Another (confirmed) hung mged (stuck/inf loop).
* annotation bugs:
in sph1.s sph 0 0 0 10
in ann1.s annot 0 0 0 test1 10 10 3 1
in ann2.s annot 30 30 30 test2 40 40 3 1
# ann2.s's label looks wrong, points at origin?
in ann3.s annot 0 0 0 1 10 10 3 1
# using numbers for a label results in no label
* rtedge with perspective is wrong. it fills in nearly entire faces,
vertically in particular. it's worse on small sized renders, and
gets better the larger the render size (indicating there's some
neighbor distance coming into play that is not affected by
max_dist). eoes not happen in non-perspective ray-traces.
* get_regions tcl command doesn't respond well to situations where
child object names in combs have dashes (the "-" character) in
names. It tries to interpret the dash as an argument delimiter.
Looks like this may be only in situations where the "-" is the
lead character and on Windows? Been hard to reproduce...
* dsp does not facetize correctly with zero elevation areas in the
data - need robustness improvements
* dsp primitives specifying data using Windows style file paths
don't work.
* attempting to create a dsp using a binary object caused a crash on
Linux - need to figure out if this was caused by feeding it the wrong
kind of binary object or some other error...
* screengrab on windows does not work
* Recursive submodel predictably goes infinite, need stack-based
db_walk_tree(): mged> in submodel submodel submodel grid test.g
* ogl display manager and framebuffer are creating windows with
transparent backgrounds (the glClear color is not being drawn) on
Linux. Presumably a driver-related issue, alpha channel, or expose
event issue. Inspecting further, it may be related to environments
where shmget() fails (or is requested via /dev/oglp) and we get
private memory -- looks like private memory is not initialized
(observed on Mac 10.6, Windows, and Ubuntu Linux using 7.26).
* fblabel seems quite busted, at least talking to a /dev/X fbserv, in
that it only draws the first character and eventually displays
rem_read() failures when run in -d debug mode.
* rtedge doesn't refresh a /dev/X fbserv (presumably double-buffered)
after doing an overlay render. it does draw, though, as confirmed
by a forced fb-fb refresh.
* typing 'comb -f -r assembly_name' shuts down mged with the error:
ERROR: bad pointer 0000000000B4CA50: s/b bu_external(x768dbbd0), was bu_vls(x89333bbb), file ..\..\..\brlcad_src\src\libbu\parse.c, line 2443"
And on the mged command line:
rt_db_cvt_to_external5 expecting non-NULL name parameter
wdb_export((null)): solid export failure
* report of mged command history not working with the down arrow key
in 7.25.0 (on Windows, unknown on other platforms). Up arrow works
fine.
* wgl framebuffer is not lingering on windows (regardless of using
wgll or default) when it should
* report of LIBBU not working when accessed by a multithreaded
application on Windows. reportedly due to some problem with the
debug memory queue.
* report of g-iges crashing (on Windows) when exporting a 1.2MB BoT
mesh (presumably imported via stl-g). worked for smaller models.
* autoview [scale] isn't updating the wireframe when opening a
database, drawing geometry, then running autoview. the status bar
shows the scale change, but the graphics window remains unaffected
unless you run "view size" to set it.
* overlay command reports an error when trying to load a file
names edges.pl, but succeeds when the file is called patches.pl
Need to see why edges.pl is not accepted.
* step-g crashing on mac with lazy symbol load failure missing:
brlcad::SurfaceTree::SurfaceTree(ON_BrepFace*, bool, int)
* metaball tessellation enters either an infinite loop or an absurdly
long tessellation process - observed on Linux 64 bit system - quick
test:
rm -f metaball.g && mged -c metaball.g "make m.s metaball; facetize m.bot m.s"
* corruption/crash issue rendering terra.g without terra.dsp,
possibly/probably parallel-related in libbn/noise.c's
bn_noise_turb() function. gdb eventually catches a segfault in
find_spec_wgt() loop with indications of corrupted memory. valgrind
confirms corrupted memory (8 bytes) after a build_spec_table()
realloc within find_spec_wgt() but it's not clear why. etbl
book-keeping seems okay.. corrupted read consistently detected on
spec_wgts = ep->spec_wgts line in bn_noise_turb(). observed on
64-bit linux system:
rm -f terra.pix && valgrind bin/rt -o terra.pix -P1 -H3 -s1024 share/brlcad/7.21.0/db/terra.g all.g
[HARD] valgrind-confirmed 8-byte corruption after a build_spec_table()
realloc in find_spec_wgt(), where "bookkeeping seems okay" -- i.e.,
root cause is non-obvious. Classic hard-to-pin data race.
[FAN-OUT: poor -- a single heisenbug needing one careful
investigator, not parallel coverage.]
* mged 'joint' hold command isn't working. looks like the fp_names
book-keeping is fuxored or the db_lookup is returning NULL (or isn't
yet performed).
* encountered a crash during rtarea on a (default) facetized version
of the hyp from the proc-db csgbrep tool.
* raytracing rhc crashes (inside malloc, so previous memory badness)
with normal tolerance set to non-default value (e.g. tol norm 0.1);
also fails (non-crash) if absolute tolerance is changed (e.g., tol
abs 0.1)
* revolve raytracing seems to be busted.. at least with the example
csgbrep revolve shape
* torus with a near zero inner diameter results in zero-length edges
during tessellation.
* report that "keep" sometimes results in a .g file with unknown units;
dbconcat also is reported to set the units to unknown if concatting
a file with unknown units.
* infinite loop in rt_find_backing_dist() raytracing a BoT (without
pieces) for bot_smooth (i.e., rt_bot_smooth()). encountered inf
loop on a jetski fastgen model that was solid but unoriented, with
about 8k faces. NOTE: possibly already have a fix for this bug
pending review and testing. --CSM
* run make to create all primitives at the origin. there are raytrace
differences, crashes, and overall bad behavior between default
ungrouped "e *" view and adding all of those primitives to a single
region. Script for creating all primitives via make command:
for i in `mged -c test.g make asdf asdf 2>&1 | awk '{print $12}' | sed 's/[<>|]/ /g'` ; do mged -c test.g make $i $i ; done
mged -c test.g "g primitives *"
mged -c test.g r primitives.r u primitives
rt -a 35 -e 25 test.g primitives
rt -a 35 -e 25 test.g primitives.r
* MGED on Mac OS X 10.6 mouse bindings fail to zoom in incrementally.
Pan, zoom out, and interactive zoom work. Shift-grip bindings need
to be verified.
* rt -i -s4096 -H16 -F/dev/null boolean-ops.g all
* compilation reportedly fails when building Tcl if the path to the
source directory includes a space.
* mged/tcl "gets" command doesn't work if you run the "source" command
to read in a script that uses gets on stdin. it just hangs until
multiple sigint's are received.
* invoking mged from a system menu seems to be broken. reported by a
reliable ArchLinux user. probably exhibits cross-platform on KDE,
GNOME, or XFCE (but original environment is unknown). the bug is
undoubtedly related to mged's interactive and stdin/stdout input
detection where mged thinks it's being scripted (beginning on or
about mged.c:1150)
* Report of copy/paste not working with Tk on Windows Vista - does
work on Windows XP.
* Update/create .mgedrc results in bogus qray lines if a db is not
open when the file is created.
* MGED doesn't initialize multipane view to the documented multipane
defaults if you just open a db with multipane already enabled.
* Creating an 'extrude' via MGED gui crashes MGED.
* edcomb command seems to be busted similar to red, doesn't seem to do
anything.
* Detailed BoT model ray trace image had incorrect background pixel
values in framebuffer, off slightly by one.
* rt is consuming 100% CPU in fb_close() on a lingering ogl
framebuffer waiting to close. needs to sleep or select for a while.
* /dev/oglb 'copy mode' fails to refresh the framebuffer
* X display manager (and probably others) will lock up mged if you Z/B
while the wireframe is being actively drawn (in X_drawVList()).
reproducible by cloning havoc a dozen or more times, getting
sub-1sec fps, Z/B after rotating wireframe but before update
finishes drawing.
* report of rt aborting randomly on 64-bit with camo shader.
* mged rrt command is not respecting the view size, just does
something similar to autoview but even gets az/el wrong too.
* Windows mged build is not generating tclIndex files with all
entries. notably the pattern_gui.tcl file is not getting included
as well as a variety of others. see missing entries in
tclscripts/mged/tclIndex for examples:
https://sourceforge.net/tracker/?func=detail&atid=640802&aid=2923199&group_id=105292
* hyp tessellation routine creates bot that does not raytrace
* hyp used in a boolean with other objects (even unions) does not
raytrace
* if you attach a display manager in tk-mged, kill the window, then
quit, mged crashes on exit.
* mged segfaults when drawing lots of solids at once (e.g. draw *.s)
* mged command mode doesn't display the output of multiple
semicolon-separated commands. Only the output of the very last mged
command is displayed. Example:
mged -c moss.g "tops ; title"
mged -c moss.g "puts OK ; tops ; puts OK2 ; title ; puts DONE"
Note that this is consistent with doing the same thing on the MGED
Command Window's command prompt - if the above is a bug it is
apparently not restricted to command/classic mode.
Further investigation suggests that this is a consequence of
Tcl treating multiple commands in a single " " block as one command,
insofar as capturing the output is concerned. It probably relates
to situations where Tcl_SetResult is called where (in this case)
Tcl_AppendResult would have been better, but it is not clear whether
changing this result setting approach would cause other breakage.
* mged rotation halts after a few events and after zooming in/out at
least once (Mac OS X 10.5)
More info: This problem appears to be specific to a particular
X11 version or versions - it has been observed with
xorg-server-1.4.2-apple33 on 10.5. It does not occur with the
community XQuartz 2.5.0 (xorg-server 1.7.6), nor does it occur
when Tk 8.5.8 is compiled to use the Aqua backend. At least one other
(possibly earlier) version of X11 from Apple on a 10.5 Mac did not
exhibit bad rotate behavior. The problem is not specifically the
zooming action - rather, the zoom triggers
a Tk focus call on the display manager window (rather than the
Tk parent window) and the problem manifests when focus is on the
display manager window. mged classic mode, where there is no
parent window, exhibits the bad rotate behavior immediately.
* infinite light sources close to objects result in unexpected/bad
light behavior. example is a 1m sph light about 5m from a box about
1k x 1k x 1k in size. setting make each light be red, green, and
blue respectively, set to infinite (and fraction 10) and sides to
the cube will render sides with a fixed color (green, blue) and top
magenta. On one test with all lights at fraction 1.0 and only one
inf, was getting interleaved partial flat/no color all around cube.
* fastgen plate mode bots are reporting invalid shotline segments.
depending on whether you shoot from the front or back can result in
bogus lists visible with nirt in mged, entirely missing the bot, or
mismatched entry/exit/overlap segments.
* tab completion in classic/command mode sometimes doesn't work
(presumably if mged can't find tcl resources). was finally able to
reproduce this with the result given as:
invalid command name "bind"
* mged 'facetize -n' command is giving many errors:
ERROR: color index out of range (-128 > 255)
and it shouldn't. seems to be happening on 3-manifold surfaces but
only for particular faces. looks like the painting algorithm that is
being used is flawed (and an incomplete implementation).
* running 'keep' on too many objects (hundreds is causing a usage
statement (and not doing the keep)
* fbserv is receiving image data very slowly if the framebuffer is a
remote X24 interface. could reproduce on mac with the following:
fbserv -s1024 1 /dev/X &
rt -F1 -s1024 db/moss.g all.g
rt -F1 -i -s1024 db/moss.g all.g # 8x worse
* ls -A and/or e -A reportedly crashes on use, unverified
* File->Export seems to not work on Windows
* xpush fails to properly create a hierarchy killing existing objects
resulting in dangling references. This may have been fixed by
r69256, but a model that exposes the issue has to be tested to be
sure.
* mged on Mac OS X will crash on an X11 call if compiled against
system Tcl/Tk (at least on 10.4 linking against 8.4), see TODO
* the ray tracer fails to report LOS and sometimes even hits on a BoT
that is marked as unoriented or is inverted (even though it
sometimes will report the segments, just without LOS). this seems
to happen for bots that are neither lh or rh (they're mixed) and
causes the raytrace to fail if they're set to anything other than
'no' for orientation. this affects rt, nirt, et al.
* g-vrml ignores bots that are created with dxf-g
* Mac OS X installer doesn't include the symbolic links, only
including the versioned installation directory.
* Mouse cursor turns into a huge yellow-translucent arrow when running
MGED through remote X11.
Running this fixes the bug: .id_0t config -cursor "xterm black"
* mged (on debian) is reporting this when the user presses tab:
Error in bgerror: invalid command name "::swidgets::togglearrow"
the second time they press tab, they get:
Error in bgerror: window name "_secErrorDialog" already exists in parent
The problem was noticed on 7.12.4 and happens regardless of there
being a db opened or not. The problem does not occur in classic
mode.
* mged command window is showing up as an empty 0x0 dimensioned window
on freebsd using xfce and metacity (single display, 1680x1050 res).
dm shows up just fine.
* g2asc of a v4 is apparently writing out the wrong s_cgtypes and
otherwise parsing v4 .g files incorrectly
* bump shader seems to be busted. only renders as flat by itself and
stacked with phong it seems to ignore the uv settings.
* the graphics window does not acquire keybinding focus in mged on
ubuntu linux. key events go to the command window even with the
graphics window has focus.
* mged tab-completion doesn't work if the object names have spaces
* Open dialog in MGED seems rather busted for scrolling and selection
(seems to be Mac OS X specific)
* turning on Framebuffer->Rectangle Area in mged disables the
embedded framebuffer display on Mac OS X when you sweep a raytrace
rectangle. sweeping still works if you leave it at All.
* invalid shaders result in an "Unable to locate where BRL-CAD ... is
installed" message that refers to being unable to find a
/lib/libSHADER.so file. Quite a bogus message and probably not
something that should abort the ray-trace.
* rtedge seems to get stuck in a loop at the end of rendering, never
terminates (unless you rtabort/kill the process); works with -P1
* nirt/query_ray reports intersection messages in triplicate if the
shot routines miss but still print out messages
* mged's plot tool (the gui one, not the 'plot' command) outputs a
plot file that has an erase as the last command, causing empty plots
* interactive mouse edits in mged can go haywire on Mac OS X with
snap-to-grid enabled
* overlap tool in mged encourages very inefficient CSG operations
(e.g. a simple bolt with an entire hull armor subtracted)
* permute (in mged) requires apply or save before 'new' vertex values
will function properly as keypoints.
* facedef then move face undoes the facedef in mged
* dsp primitive is going into what seems to be an unbounded memory
allocation loop during prep, inside dsp_layers().
* libfb cannot open a file descriptor when piping/redirecting output.
OK: rt -F/./dev/stdout moss.g all.g
BAD: rt -F/./dev/stdout moss.g all.g > test.pix
* ray-tracers assume a seekable output stream. libfb reports numerous
fseek errors and outputs slightly corrupted pix data.
OK: rt -o test.pix moss.g all.g && pix-png test.pix > test.png && rm -f test.pix
BAD: rt -o /dev/stdout moss.g all.g | pix-png > test.png
* running any of the various mged commands (e.g. clicking the raytrace
button many times quickly, or running rtarea on a large model) that
output a lot of data will hang mged (idle cpu utilization).
* solids.sh regression test fails on Mac OS X with one pixel
off-by-many on the edge of the middle ARB8 when using an optimized
-O3 compile (-fno-unsafe-math-optimizations makes no difference)
* triangulation of some pipe in toyjeep.g fails (rather reliably) on
some given bend. fails in nmg_triangulate model().
* debugbu 2 immediately reports a bu_vls_free() error.. apparently
been a problem since 4.5 days. this occurs because
bu_memdebug_add() is not called unless memory checking is enabled
via bu_debug. so when bu_debug is set to 2 or 3, it ends up
reporting errors during bu_free() for items that were allocated and
were not yet being tracked.
* mged View menu says I and O are keybindings for zoom in/out -- they
are apparently not.
* raytracers report the wrong amount of cumulative time (reports as
0.0 seconds elapsed) on amd64 linux; most likely the same pthread
accounting bug visited a couple years ago.
* Create menu.. create "part" boo hiss..
* fbed is looking for /usr/lib/vfont/nonie.r.12
* mged doesn't check if html_dir does not exist when searching for
docs/browser.
* permute then translate doesn't refresh the graphics window
permute 4378
translate menus
p 0 0 0
p 0 0 0
* constrained axis translation bindings on OS X don't work
object/matrix edit
shift-alt mouse (left/mid/right for x/y/z respectively) should work
* the findfont directive in gv postscript is reporting font not found
* concave arbs give correct wireframe but do not raytrace correctly.
* mged's solid illuminate doesn't work when Lighting is turned on
* raytrace of zoomed images (e.g., -s64) doesn't work for if_X24
framebuffers. zooming logic seems to be broken (was crashing in
memcpy, but that was fixed) for at least -s96 and smaller:
./libtool --mode=execute gdb --args src/rt/rt -F/dev/X -P1 -s64 db/moss.g all.g
* g2asc exports attr lines but will not grok them on asc2g
* mged's matrix selection does not modify the correct matrix if there
are multiply referenced non-unique paths (e.g. referencing the same
object N times in a combination).
* facetize -t doesn't work (tnurb support)
* on os x, the -fast option results in an odd optimization/aliasing
bug where rtip contents are lost in rt after returning from
rt_gettrees().
* tra in console mode outputs a warning about mged_players
* mged primitive editor doesn't accept/apply values to disk for
certain primitives (e.g. sph)
* enabling perspective mode horks shaded mode, also Z clipping
shouldn't be required to get the shading.
* an underlay framebuffer does not underlay with shaded mode
* rtarea gives incorrect areas when using -H hypersample flag
* setting src/librt/db5_io.c's AVS_ADD off in db5_import_attributes
causes bad things to happen and it really shouldn't.
* vrml exporter (and probably others) doesn't export primitives
directly as one might expect like the ray-tracers, only regions.
* sketches extruded with non-square AB vectors results in inner sketch
components not getting scaled properly.
* bot-bldxf fails in db_walk_tree(), interface may have changed
---
Bugs should be reported to the bug tracker on the project website at
http://sourceforge.net/tracker/?atid=640802&group_id=105292
BUGS should be formatted to column 70 (M-q in emacs), no tabs.
// Local Variables:
// mode: Text
// fill-column: 70
// End:
-87
View File
@@ -1,87 +0,0 @@
= BRL-CAD Interface Change Policy
:toc: macro
toc::[]
== Scope
This policy defines how BRL-CAD public interfaces may change. Public
interfaces include developer APIs, command-line interfaces, graphical
interfaces, documented commands, installed headers, public macros,
public types, and other behavior users reasonably rely on.
Renaming an application is not minimally impacting: an application
name is the primary way users find and run the tool.
Every public interface change must be either minimally impacting or
formally deprecated.
== Minimally Impacting
A minimally impacting change may be made at any time. A change is
minimally impacting only when it can be represented by the documented
rule language in
link:doc/changes/minimally-impacting.rules[doc/changes/minimally-impacting.rules]
and emitted by the generated update script.
If the rule language cannot express a change, either extend the rule
language so the generated script can perform the update, or treat the
change as formally deprecated.
Minimally impacting path includes:
* recently introduced interfaces that have not yet appeared unchanged
in two releases;
* appreciably broken interfaces that have been unusable for at least
two releases and have no secondary utility;
* elementary mechanical changes such as renames, parameter reordering,
parameter removal, defaulted parameter insertion, equivalent
interface substitutions, and header moves.
For function argument rewrites, BRL-CAD assumes callers are not
relying on preprocessor-generated call syntax and are not passing
nested function calls as arguments to the changed function. That
assumption keeps generated substitutions deterministic and reviewable.
Rule syntax and generated update-script workflow are documented in
link:doc/changes/README.adoc[doc/changes/README.adoc]. The generated
build-tree rendering of minimally impacting changes is
`doc/changes/minimally-impacting.adoc`.
== Formally Deprecated
Any public interface change that is not minimally impacting must
follow the formal deprecation process.
During a major release, such as 7.x to 8.x, any public interface may
change without advance notice. Major version changes imply interface
incompatibility.
During a minor release, such as 7.44.x to 7.46.x, a public interface
must be deprecated beforehand with advance notice in at least two
minor releases and at least 90 days elapsed since the initial release
announcement.
Public interfaces scheduled for change should be listed in
link:doc/changes/deprecated.adoc[doc/changes/deprecated.adoc] and
visibly marked in the source code. Appropriate markings include
`DEPRECATED` declarations, preprocessor warnings, `@DEPRECATED`
comments, runtime warnings when they do not disrupt valid usage, and
documentation updates.
After a deprecation window has completed, removed or significantly
changed interfaces are listed in
link:doc/changes/obsoleted.adoc[doc/changes/obsoleted.adoc].
== Examples
Removing `rt_shootray()` after it has been published and documented in
multiple releases is not minimally impacting unless a generated rule
can update callers to an equivalent interface. Otherwise, it must be
listed as deprecated, marked in the headers, announced in releases,
and only later obsoleted.
Renaming `bu_log()` or adding a defaulted first argument can be
minimally impacting if the change is listed in
`minimally-impacting.rules` and the generated update script rewrites
existing callers.
-3430
View File
File diff suppressed because it is too large Load Diff
-116
View File
@@ -1,116 +0,0 @@
BRL-CAD Copying and Distribution
================================
BRL-CAD is Open Source software with copyright primarily held by the
U.S. Government. The source code is controlled and maintained by a
core team of Open Source developers working around the world. Those
core developers operate under a meritocracy organizational structure
adhering to developer guidelines outlined in the HACKING developer's
guide and to the legal conventions and requirements outlined in this
document.
As a unified work, BRL-CAD is made available under the terms of the
GNU Lesser General Public License (LGPL) as published by the Free
Software Foundation.
As distinctly organized and separate components, parts of BRL-CAD are
made available under different licenses for different portions
including the BSD license and files in the public domain. The Overview
section describes how the various licenses apply to the different
portions of BRL-CAD.
BRL-CAD is distributed in the hope that it will be useful, but WITHOUT
ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public
License for more details.
You should have received a copy of the GNU Lesser General Public
License along with this file. If you did not, please contact one of
the BRL-CAD project administrators listed at the Github project
site https://github.com/BRL-CAD/brlcad/ or listed in the AUTHORS file
included as part of the distribution.
Overview
--------
BRL-CAD consists primarily of libraries, applications, scripts,
documentation, geometric models, images, data resources, and build
infrastructure. The BRL-CAD libraries provide their headers in the
include/ directory as well as all of the directories that begin with
the prefix "lib" in the src/ directory (e.g. src/librt/). All of
BRL-CAD's libraries, applications, and any content lacking a license
specification are covered by the terms of the LGPL.
Most of BRL-CAD's build infrastructure including files required by
the GNU Build System (such as the CMakeLists.txt files), a variety
of scripts located in the misc/ and sh/ directories, and the testing
infrastructure (scripts and resources) are provided either under
the BSD license or are in the public domain. Similarly, most of
the geometric models, images, and other data resources are also
provided under the BSD license. Refer to each individual file for
specific terms.
BRL-CAD's documentation consists of manual pages located throughout
the package, most of the files in the doc/ directory, and the
top-level administrative project text files (e.g. README & AUTHORS).
Unless otherwise denoted, all of BRL-CAD's documentation is made
available under the terms of the BSD Documentation License (BDL) or
are in the public domain. Refer to each document for specific terms.
The full text of the LGPL, BDL, and BSD license should be included in
the source distribution of BRL-CAD in the doc/legal/ directory. Refer
to the full license text for more details, information, requirements,
and implications of each license.
3rd-Party Components
--------------------
The BRL-CAD package utilizes and redistributes several 3rd party
source codes, libraries, and applications. Said 3rd party source
code, libraries, and applications all retain their respective
agreements, licenses, and copyrights and should be referred to
individually for their specific terms. For the purposes of
redistribution and legal compatibility for all of BRL-CAD's existing
user base, NO 3RD PARTY LIBRARIES SHALL BE INCLUDED THAT ARE UNDER THE
TERMS OF THE GNU GENERAL PUBLIC LICENSE or any other license with
similar legal implications that would impose legal obligations on
external codes that utilize BRL-CAD as a library.
When referring to BRL-CAD, its source code, documentation, and
libraries, the reference is not meant to include or imply 3rd party
source code, libraries, and/or applications unless specifically stated
otherwise. No endorsement or claim of authorship is implied to any
3rd party asset that is included with BRL-CAD.
Copyright
---------
All contributions to BRL-CAD have been provided under agreement. By
requiring all contributions be given back to the BRL-CAD developers,
this agreement allows the BRL-CAD project to continue to grow
unhindered. As such, a majority of the source code is copyright by
the United States Government as represented by the United States Army
Research Laboratory.
Authors and other BRL-CAD contributors must comply with the copyright
terms for their respective contributions unless otherwise noted or
arranged. This includes an implicit assignment of copyright for any
and all contributions being made. The following notice should be
prominent in the BRL-CAD sources:
Copyright (c) 1984-2026 United States Government as represented by
the U.S. Army Research Laboratory.
Contact
-------
Questions or comments regarding BRL-CAD legal issues pertaining to
copying, linking, licensing, trademark, or otherwise should be
directed to the BRL-CAD Development Team at the following address:
BRL-CAD Development Team
devs@brlcad.org
http://brlcad.org
---
$Revision$
+28
View File
@@ -0,0 +1,28 @@
Re-distribution of this software is restricted, as described in your
"Statement of Terms and Conditions for the Release of The BRL-CAD
Package" agreement.
Portions of this software and the associated databases and images are
Copyright (C) 1985-2004 by the United States Army in all countries
except the USA. Unauthorized redistribution in any form is
prohibited. Recipients of this distribution are authorized unlimited
use within their corporation, organization, or agency.
The mark "BRL-CAD" is a Registered Trademark of the United States
Army. All rights reserved.
There is no warranty or other guarantee of fitness for this software,
it is provided solely "as is". Bug reports or fixes must be sent to
ARL, which may or may not act on them.
This software was developed by and is proprietary to the United States
Government, and any use of the software without the written permission
of the US Army Research Laboratory is strictly prohibited. Any
unauthorized use of the software will be construed as an infringement
of the Government's rights and will subject the unauthorized user to
action(s) for infringement damages. (BRL MFR 380-15, Feb-88)
The software in the "contributed" directory is Public Domain,
Distribution Unlimited. In addition, certain other modules in the
BRL-CAD package bear this designation. Files so marked are available
for unlimited use.
+14
View File
@@ -0,0 +1,14 @@
/*
* Top level Cakefile.
*
* This Cakefile serves the same purpose as the top level Makefile,
* ie, to run the "gen.sh" script with the given argument.
*
* $Header$
*/
%&:
/bin/sh gen.sh %
all&::
/bin/sh gen.sh
+92
View File
@@ -0,0 +1,92 @@
/*
* C A K E F I L E . L I B
*
* Cakefile for building a single library archive.
* Symbol PRODUCTS should be name of a single library
*
* Author -
* Michael John Muuss
*
* Source -
* SECAD/VLD Computing Consortium, Bldg 394
* The U. S. Army Ballistic Research Laboratory
* Aberdeen Proving Ground, Maryland 21005-5066
*
* Distribution Status -
* Public Domain, Distribution Unlimitied.
*
* $Header$
*/
#ifndef PRODUCTS
# include "Symbol PRODUCTS required to make library"
#endif
#ifndef SRCDIR
# include "Symbol SRCDIR required"
#endif
#ifndef OBJ
# include "Symbol OBJ required"
#endif
#ifndef VERSION_VARIABLE
# include "Symbol VERSION_VARIABLE required"
#endif
#ifndef LIBRARY_TITLE
# include "Symbol LIBRARY_TITLE required"
#endif
#ifndef EXTRA_OBJ
# define EXTRA_OBJ /**/
#endif
#ifndef EXTRA_SETUP
# define EXTRA_SETUP /**/
#endif
#ifndef EXTRA_OBJ_NO_DEPENDENCY
# define EXTRA_OBJ_NO_DEPENDENCY /**/
#endif
#ifndef LIB_FLAGS
# define LIB_FLAGS /**/
#endif
#if !defined(BUILD_LIBRARY)
PRODUCTS:: EXTRA_OBJ OBJ
newvers.sh VERSION_VARIABLE LIBRARY_TITLE
CC CFLAGS -c vers.c
rm -f PRODUCTS; EXTRA_SETUP
AR r PRODUCTS OBJ EXTRA_OBJ EXTRA_OBJ_NO_DEPENDENCY vers.o
RANLIB PRODUCTS
/* If RANLIB is specified, be sure it is run when installing libraries */
# define AFTERINSTALL RANLIB
#else
/* Shared library support.
* Can't list SHARED_PRODUCT in 'rm' command, or will get wrong version number.
* (Cake won't re-run the LIBVERS shell script)
* If non-null, LIBVERS will start with a leading dot.
* Note that the RM command zaps anything starting with PRODUCTS.
* Note that if you have shared libraries, you better have symlinks.
*/
# define SHARED_PRODUCT PRODUCTS''[[LIBVERS]]
PRODUCTS&:: EXTRA_OBJ OBJ
newvers.sh VERSION_VARIABLE LIBRARY_TITLE
CC CFLAGS -c vers.c
rm -f PRODUCTS*; EXTRA_SETUP
BUILD_LIBRARY SHARED_PRODUCT OBJ EXTRA_OBJ EXTRA_OBJ_NO_DEPENDENCY vers.o
sharedliblink.sh SHARED_PRODUCT
/* Use this opportunity to build the symlink on install */
# define AFTERINSTALL sharedliblink.sh
#endif
%.o&: SRCDIR,,%,o if exist ../SRCDIR/%.c
%9,,%,o&: ../%9/%.c HDR_DEP9 if exist ../%9/%.c
CC CFLAGS LIB_FLAGS -c ../%9/%.c
/* Override the modes for the library */
#undef BINDIR
#undef BINPERM
#define BINDIR LIBDIR
#define BINPERM LIBPERM
+269
View File
@@ -0,0 +1,269 @@
/*
* C A K E F I L E . R U L E S
*/
/*
* Patterns to handle the installation and uninstallation
* of products, manuals, and manual stubs.
* This is complicated by the fact that not all directories
* will contain all three types of items.
*/
#define MAN_EXISTS {{ls ../SRCDIR|grep -s .MANSECTION'$'}}
#define STUB_EXISTS {{ls ../SRCDIR|grep -s .MANSECTION.stub'$'}}
#define ARG_EXISTS {{ARGS="%"; test '%' != "$ARGS" -o -f %}}
/* Format sources for printing on stdout. Use macro to bypass ANSI cpp "bug" */
#define PRINT_STUFF [[SUB X X.print ../SRCDIR/Cakefile ]] \
[[SUB X X.print ../SRCDIR/''*.[h''MANSECTION] ]] \
[[SUB X X.nroff ../SRCDIR/''*.MANSECTION ]] \
[[SUB X ../SRCDIR/X''SRCSUFF.print FILES]]
print&: PRINT_SUFF
%.print&: do-%.print if ARG_EXISTS
%.print&: if not ARG_EXISTS
do-%.print&:
@pr %
/*
*/
nroff&: do-nroff if MAN_EXISTS
nroff&: if not MAN_EXISTS
do-nroff&: [[SUB X X.nroff ../SRCDIR/''*.MANSECTION ]]
%.nroff&: ../SRCDIR/%
@nroff -Tlp -man ../SRCDIR/%
/*
* Typeset all the non-stub manual pages. Do them all at once,
* to prevent lots of extra header sheets on the printer
*
* do-typeset-a creates the file "troff.out" with the macros in it
* %.troff adds each manual page to "troff.out"
*/
typeset&: do-typeset if MAN_EXISTS
typeset&: if not MAN_EXISTS
do-typeset&: do-typeset-a troff.out
( TYPESET_MAN2 ) < troff.out
@rm -f troff.out
do-typeset-a&:
TYPESET_MAN0 TYPESET_MAN1 > troff.out
troff.out&: [[SUB X X.troff ../SRCDIR/''*.MANSECTION ]]
%.troff&: if ARG_EXISTS
TYPESET_MAN0 % >> troff.out
#define SRC_LIST `SUB X ../SRCDIR/X''SRCSUFF FILES`
lint&:
LINT LFLAGS -I''INCDIR SRC_LIST LLIBES > SRCDIR.lint
tags: [[echo SRC_LIST]]
ctags SRC_LIST
TAGS: [[echo SRC_LIST]]
etags SRC_LIST
flow&: [[echo SRC_LIST]]
cflow -I''INCDIR SRC_LIST > SRCDIR.flow
xref&: [[echo SRC_LIST]]
cxref -c -s -w132 -I''INCDIR SRC_LIST > SRCDIR.xref
compare&: [[SUB X X.compare PRODUCTS]]
%.compare&: %
cmp BINDIR/% %
#if !defined(DONT_INSTALL)
uninstall&: uninstall-prod uninstall-man uninstall-stub
#else
uninstall&:
#endif
#ifdef PRODUCTS
uninstall-prod&: [[SUB X X.uninstall-prod PRODUCTS]]
#else
uninstall-prod&:
#endif
%.uninstall-prod&:
rm -f BINDIR/% BINDIR/%.bak
uninstall-man&: do-uninstall-man if MAN_EXISTS
uninstall-man&: if not MAN_EXISTS
do-uninstall-man&: [[SUB ../SRCDIR/X X.ui-man ../SRCDIR/''*.MANSECTION]]
%.ui-man&:
rm -f MANDIR''MANSECTION/% MANDIR''MANSECTION/%.bak
uninstall-stub&: do-uninstall-stub if STUB_EXISTS
uninstall-stub&: if not STUB_EXISTS
do-uninstall-stub&: [[SUB ../SRCDIR/X.stub X.uninstall-stub ../SRCDIR/''*.stub]]
%.uninstall-stub&:
rm -f MANDIR''MANSECTION/% MANDIR''MANSECTION/%.bak
#if !defined(EXTRA_INSTALL_TARGETS)
# define EXTRA_INSTALL_TARGETS /**/
#endif
#if !defined(DONT_INSTALL)
install&: install-prod install-man install-stub
install-nobak&: install-prod-nobak install-man install-stub
#else
install&:
install-nobak&:
#endif
#if defined(SHARED_PRODUCT)
install-prod&: [[SUB X X.iprod SHARED_PRODUCT]] EXTRA_INSTALL_TARGETS
install-prod-nobak&: [[SUB X X.iprod-nobak SHARED_PRODUCT]] EXTRA_INSTALL_TARGETS
#else
# if defined(PRODUCTS)
install-prod&: [[SUB X X.iprod PRODUCTS]] EXTRA_INSTALL_TARGETS
install-prod-nobak&: [[SUB X X.iprod-nobak PRODUCTS]] EXTRA_INSTALL_TARGETS
# else
install-prod&:
install-prod-nobak&:
# endif
#endif
/* Here is where we depend on having /bin/sh as the shell */
%.iprod&: %
@echo ......checking % 1>&2 ; \
if cmp -s BINDIR/% %; \
then exit 0; fi; \
mv -f BINDIR/% BINDIR/%.bak 2>/dev/null; \
if INS % BINDIR/%; \
then if test x''AFTERINSTALL != x'AFTERINSTALL'; \
then AFTERINSTALL BINDIR/%; fi; \
echo "++++++INSTALLED" BINDIR/% 1>&2; \
chmod BINPERM BINDIR/%; \
fi
%.iprod-nobak&: %
@echo ......checking % 1>&2 ; \
if cmp -s BINDIR/% %; \
then exit 0; fi; \
rm -f BINDIR/% 2>/dev/null; \
if INS % BINDIR/%; \
then if test x''AFTERINSTALL != x'AFTERINSTALL'; \
then AFTERINSTALL BINDIR/%; fi; \
echo "++++++INSTALLED" BINDIR/% 1>&2; \
chmod BINPERM BINDIR/%; \
fi
install-man&: do-install-man if MAN_EXISTS
install-man&: if not MAN_EXISTS
do-install-man&: [[SUB ../SRCDIR/X X.i-man ../SRCDIR/''*.MANSECTION ]]
%.i-man&: ../SRCDIR/%
@if cmp -s MANDIR''MANSECTION/% ../SRCDIR/%; \
then exit 0; fi; \
mv -f MANDIR''MANSECTION/% MANDIR''MANSECTION/%.bak 2>/dev/null; \
if INS ../SRCDIR/% MANDIR''MANSECTION/%; \
then echo "++++++INSTALLED" MANDIR''MANSECTION/% 1>&2; \
chmod MANPERM MANDIR''MANSECTION/%; \
fi
install-stub&: do-install-stub if STUB_EXISTS
install-stub&: if not STUB_EXISTS
do-install-stub&: [[SUB ../SRCDIR/X.stub X.install-stub ../SRCDIR/''*.stub]]
%.install-stub&: ../SRCDIR/%.stub
@if cmp -s MANDIR''MANSECTION/% ../SRCDIR/%.stub; \
then exit 0; fi; \
mv -f MANDIR''MANSECTION/% MANDIR''MANSECTION/%.bak 2>/dev/null; \
if INS ../SRCDIR/%.stub MANDIR''MANSECTION/%; \
then echo "++++++INSTALLED" MANDIR''MANSECTION/% 1>&2; \
chmod MANPERM MANDIR''MANSECTION/%; \
fi
/*
* Force installation of copies of all sources,
* whether configured in or not, into the distribution tree.
*/
#ifndef STATIC_PRODUCTS
# define STATIC_PRODUCTS /**/
#endif
#ifdef NFS
#define INSTALL_PATTERNS STATIC_PRODUCTS \
../SRCDIR/Cakefile ../SRCDIR/\\\\*.[hcsfyl] \
../SRCDIR/\\\\*.sh \
../SRCDIR/\\\\*.MANSECTION ../SRCDIR/\\\\*.MANSECTION.stub \
../SRCDIR/\\\\*.doc
#else
#define INSTALL_PATTERNS STATIC_PRODUCTS \
./Cakefile \\\\*.[hcsfyl] \\\\*.sh \
\\\\*.MANSECTION \\\\*.MANSECTION.stub \\\\*.doc
#endif
/* inst-dist is never run automatically, it has to be run by hand. */
/* inst-dist is run from gen.sh as part of the final packaging of a distribution */
inst-dist&: dist-clobber [[SUB X X.do-inst-dist INSTALL_PATTERNS]]
dist-clobber&:
-rm -fr DISTRIBUTION/SRCDIR
mkdir DISTRIBUTION/SRCDIR; chmod 775 DISTRIBUTION/SRCDIR
%.do-inst-dist&: %.inst-dist if ARG_EXISTS
%.do-inst-dist&: if not ARG_EXISTS
%.inst-dist&:
-INS % DISTRIBUTION/SRCDIR/.
#ifndef EXTRA_CLEAN
# define EXTRA_CLEAN /**/
#endif
/*
* clean remove all .o files and by-products
* noprod remove the final executables
* clobber perform clean & noprod
*/
clobber&: clean noprod
clean&:
-rm -f core *.core *~ *.o EXTRA_CLEAN SRCDIR.out SRCDIR.err SRCDIR.xref SRCDIR.flow SRCDIR.lint
#if defined(LIBRARY_TITLE)
/*
* The asterisk is to glob all the variations of (shared) library names.
* This depends on the fact that for libraries, PRODUCTS is a single name,
* not a list of file names, and that there will be no source file called
* PRODUCTS.c, e.g., no librt.c file for making librt.so.10.
*
* The "SRCDIR.*" version is to catch the case where we're changing
* from shared libraries to non-shared libraries.
*/
noprod&:
-rm -f PRODUCTS* SRCDIR.*
#else
noprod&:
-rm -f PRODUCTS
#endif
#ifdef never
/*
* Insist that, by default, Cake work on making the products.
* THIS SHOULD BE THE LAST THING CAKE SEES!
* The double-colon marks this as the main target.
*/
"!MAINCAKE!"&:: PRODUCTS
#endif
-10987
View File
File diff suppressed because it is too large Load Diff
-1680
View File
File diff suppressed because it is too large Load Diff
+34 -463
View File
@@ -1,476 +1,47 @@
The Installation Guide to BRL-CAD
=================================
To compile and install the BRLCAD source, perform the following steps:
This document covers the installing BRL-CAD from either a source or binary
distribution. Please see REPORTING PROBLEMS to troubleshoot.
% mkdir /usr/brlcad
Some platforms have additional platform-specific documentation provided in the
doc/ directory with additional information. This presently includes the
following:
If you choose a directory other than /usr/brlcad, you will need to set the
environment variable BRLCAD_ROOT to be the name of this directory. Because a
number of paths are compiled into the package, it is not possible to compile
the package for one location, then move it to another. Be sure that
/usr/brlcad/bin or $BRLCAD_ROOT/bin is in your shell path. For example:
doc/README.BSD -- FreeBSD, NetBSD, OpenBSD, etc.
doc/README.Linux -- Various Linux distributions
doc/README.MacOSX -- Apple Mac OS X
doc/README.Solaris -- Oracle Solaris, OpenIndiana (Illumos), etc.
doc/README.VAX -- Virtual Address eXtension architecture from DEC.
One of the original BRL-CAD platforms. These
days, re-created using the simh simulator.
doc/README.Windows -- Microsoft Windows
sh:
BRLCAD_ROOT=/foobar/brlcad
PATH=$PATH:/foobar/brlcad/bin
export PATH
csh:
setenv BRLCAD_ROOT /foobar/brlcad
set path=($path /foobar/brlcad/bin)
Compile:
% cd /foobar/brlcad
% sh setup.sh
TABLE OF CONTENTS
-----------------
Introduction
Table of Contents
Quick Source Install
Installing from Binary
Installing from Source
Testing Functionality
Post-Installation
Reporting Problems
Configuration Options
The next step can take a considerable amount of time on some systems:
sh:
make > make.log 2>&1
csh:
make >& make.log
Install:
Review the log of compilation, then run:
QUICK SOURCE INSTALL
--------------------
make install
See https://brlcad.org/wiki/Compiling for a platform-specific walk-through
including instructions for building on Windows.
This process should proceed without problems on the following systems:
Required tools:
- Git must be 2.17 or later
- CMake must be 3.26 or later
- Compiler must be C++17-compliant
- If using Visual Studio, version 2019 (16.8+) or later
- If using GCC/G++, version 7 or later
- If using LLVM/Clang 5 or later
- If using Intel, version 19.0.1 or later
RedHat Linux 7.2
FreeBSD 4.5
SunOS 5.8 (Solaris)
Irix 6.5
Mac OS X (With X11 installed -- INSTALL.pmac for details)
Steps to compile, test, and install an optimized BRL-CAD on non-Windows
platforms:
For binary and source download instructions see:
git clone https://github.com/BRL-CAD/brlcad.git
mkdir brlcad/build
cd brlcad/build
cmake .. -DENABLE_ALL=ON -DCMAKE_BUILD_TYPE=Release
make -j4
make check
sudo make install
http://ftp.arl.army.mil/brlcad
Once installed, run bin/mged or bin/archer to launch BRL-CAD's GUI apps. See
POST-INSTALLATION for instruction adding bin/ folder to your system PATH to
more easily run geometry converters.
INSTALLING FROM BINARY
----------------------
There are a variety of different kinds of binary distributions of
BRL-CAD. Some of the binary distributions are sufficiently generic and
are simply a binary compressed tarball distribution. Others are
specific to a particular platform such as Debian, Mac OS X, FreeBSD,
and Windows etc.
Generic Binary Distributions:
For binary distributions that are simply compressed tarballs of the
installation root, they should contain the entire hierarchy of the
distribution. To put that hierarchy in its "installed" location, you just
create the directory and move the expanded tarball contents:
gunzip BRL-CAD_X.Y.Z_Linux_ia64.tar.gz
tar -xvf BRL-CAD_X.Y.Z_Linux_ia64.tar
sudo mkdir /usr/brlcad/rel-X.Y.Z
sudo mv BRL-CAD_X.Y.Z_Linux_ia64/* /usr/brlcad/rel-7.X.Y/
Of course, there are other compression options possible including zip and
bzip2. By default, BRL-CAD expects to be installed into /usr/brlcad/rel-X.Y.Z.
On some platforms the binary may be relocatable, but this is not guaranteed.
It's recommended that you start from a source distribution if you would like to
install into an alternate installation location. That said, if you do desire
to install and/or run BRL-CAD from a different location, give it a try...on
some platforms it will work.
Something to be aware of, even if a binary distribution IS relocatable: it will
use its local copies of things like libraries only so long as the "final"
installed target directory that the build was compiled for does not contain a
BRL-CAD installation. Due to the way path logic is set, an installed copy of a
library in the correct location will always be loaded first, regardless of the
presence of a "local" copy.
Mac OS X Disk Mounting Image:
Mount the .dmg and run the Installer .pkg contained therein. This will install
into /usr/brlcad/rel-X.Y.Z and will only require confirming that your
environment is set up properly (i.e. add /usr/brlcad/rel-X.Y.Z/bin to your
path) as described in the Quick Installation section.
Validating checksums:
The integrity of distributed files can be verified using checksums that are
published with released files. Released files and their checksums are
available from the GitHub releases page (https://github.com/BRL-CAD/brlcad/releases). If you
re-distribute BRL-CAD, checksums should be retained with the files so others
can validate origination.
INSTALLING FROM SOURCE
----------------------
There are a couple of ways to obtain the BRL-CAD sources, usually via one of
the following starting points:
1) from a Git checkout, or
2) from a source distribution tarball
Using the latest Git sources is recommended where possible since it
will have the latest changes.
There are many different ways to build BRL-CAD and depending on what
you need/want will determine which configuration options you should
use. See the CONFIGURATION OPTIONS section below for details on how
to go about selecting which options are appropriate for you.
BRL-CAD's dependencies are managed in a separate repository, located at
https://github.com/BRL-CAD/bext By default BRL-CAD's configure process will
download and manage the necessary dependencies, avoiding the need for user
awareness of the bext repository, but there are a number of scenarios where it
is advantageous for developers to adjust how this process works.
The full dependency stack of BRL-CAD, with all optional and experimental
features enabled, is a VERY large and long compile. Therefore, the bext build
outputs can be built as their own separate, external project to allow for reuse
of the compiled outputs. Building bext separately means BRL-CAD won't get a
chance to customize what is and is not built, but the trade-off is that outputs
can be built once and reused over and over. Doing so can significantly shorten
time spent configuring BRL-CAD builds - reusing bext compiled outputs is
recommended for serious developers.
Various useful configurations for working with bext:
* Get a git clone that has everything which might be needed (large,
but useful for offline building)
git clone --recurse-submodules https://github.com/BRL-CAD/brlcad
* Have prebuilt bext outputs to reuse - BRL-CAD will simply copy and prepare
the pre-existing files
cmake .. -DBRLCAD_EXT_DIR=/home/user/bext_output
* Already have an existing bext clone but want BRL-CAD to build bext outputs
cmake .. -DBRLCAD_EXT_SOURCE_DIR=/home/user/bext
* Download, build and bundle only what is needed for librt
cmake .. -DBRLCAD_COMPONENTS=librt
* Build and bundle only what is needed, but don't require internet for bext clone
cmake .. -DBRLCAD_EXT_SOURCE_DIR=/home/user/bext -DBRLCAD_COMPONENTS=librt
By default, the build system will prepare a Debug build and install into the
/usr/brlcad/dev-X.Y.Z directory. The CMAKE_INSTALL_PREFIX option may be used
to change that directory, or a Release build type may be specified to install
to /usr/brlcad/rel-X.Y.Z - more on this below. The tradition of non-system
installation paths goes back a couple of decades and is a convenient means to
isolate the BRL-CAD solid modeling system from your system, resolves conflicts,
facilitates uninstalls, and simplifies upgrades. The default configuration is
performed by running `cmake'. It is not required to do the build in a
directory different from your source directory, but it is much cleaner and
*highly* recommended - this guide will illustrate the build process with the
assumption that the BRL-CAD source code is in the directory brlcad-X.Y.Z and
the directory intended to hold the build output is brlcad-build, located in the
same parent directory as brlcad-X.Y.Z:
.
./brlcad-X.Y.Z
./brlcad-build
To start the build process, cd into brlcad-build and run CMake,
pointing it to the source directory:
cd brlcad-build
cmake ../brlcad-X.Y.Z
As mentioned earlier, CMake uses two "build types", controlled by
the CMAKE_BUILD_TYPE variable, that are useful for specific purposes:
* Debug (-DCMAKE_BUILD_TYPE=Debug) - Debug is the configuration that most
developers will want to use when working on BRL-CAD. It will add
debug flags to the compile, and sets the default install directory to
be /usr/brlcad/dev-X.Y.Z - in order to run the resulting installed
binaries, the developer should ensure that the dev-X.Y.Z path is
first in his or her PATH environment variable.
* Release (-DCMAKE_BUILD_TYPE=Release) - A release build is intended for
final consumption by end users and as such has optimizations enabled.
It also sets the install path to /usr/brlcad/rel-X.Y.Z - best practice
for release installation is to set up symbolic links in /usr/brlcad to
point to the most current BRL-CAD release, while allowing older versions
to remain installed on the system in case they are needed.
In both of these cases any individual variable may be overridden - for
example, setting -DCMAKE_INSTALL_PREFIX=/usr/brlcad in a Debug build will
override the ../brlcad-install default. Build types are a convenient way
to bundle sets of settings, but they do not prevent overrides if a more
custom setup is needed.
If the autodetection mechanisms fail to produce a working configuration,
the next simplest approach is typically to enable ALL the third party
components - this is typically a well tested configuration, but will
increase both the build time and final install size of BRL-CAD on
the system. To set this variable on the command line, use -D to
define ENABLE_ALL for CMake:
-DENABLE_ALL=ON
To obtain an optimized build (for example, for BRL-CAD Benchmark
performance evaluation), enable BRLCAD_FLAGS_OPTIMIZATION:
-DBRLCAD_FLAGS_OPTIMIZATION=ON
See the CONFIGURATION OPTIONS below for more details on all of the
possible settings.
Once configured, you should be able to successfully build BRL-CAD via
make:
make
(On multicore systems, adding the -j flag (e.g. -j6) is recommended)
Installing the Compilation:
After the build successfully completes and assuming the benchmark also
produces correct results, installation may begin. Like any package,
you must have sufficient filesystem permissions to install. To
install into a system location, you can generally either become a
super user via the su command and run
make install
or on operating systems set up to use sudo:
sudo make install
TESTING FUNCTIONALITY
---------------------
The primary build target to validate a compilation of BRL-CAD is:
make check
That runs a trio of test sets including "benchmark", "regress", and
"unit". The first set is a performance test that also validates
whether ray tracing behavior is correct:
make benchmark
The second test set is our regression tests that run a host of
rigorous integration tests and validate essential behavior:
make regress
The third set runs unit tests that validate low-level behavior in
BRL-CAD's core libraries:
make unit
Last but not least, one may simply run all available tests, though
note that some tests will intentionally fail:
make test
POST-INSTALLATION
-----------------
Permissions:
Something to be aware of with CMake installations is that umask settings
are ignored by current versions of CMake. It is a common situation in
Unix environments to want "group" members to have read/write access -
to achieve this, after installation the following find command can be
run (of course, substituting the actual BRL-CAD version for X.Y.Z):
find /usr/brlcad/rel-X.Y.Z -type d -exec chmod ug+rwx {} \; -exec chmod o+rx {} \; -o -type f -exec chmod ug+rw {} \; -exec chmod o+r {} \;
The above 'find' line will set up permissions across a /usr/brlcad
rooted installation such that 'user' and 'group' will have read-write
access and 'other' will have read access consistently across all
files.
System PATH:
Normally, BRL-CAD's install directories are not in system PATH lists and
consequently BRL-CAD's executables will not be invocable without specifying
their full path. This is normally handled in Unix environments by adding
the desired BRL-CAD installation's binary directory to the user's local path:
On Windows, the PATH system variable can be set using System Utility
in control panel. Add the bin/ folder in the install directory to PATH.
On Linux/BSD/other systems:
In the bash shell: export PATH=/usr/brlcad/rel-X.Y.Z:$PATH
In the csh shell: setenv PATH /usr/brlcad/rel-X.Y.Z:$PATH
REPORTING PROBLEMS
------------------
Please report any bugs, support requests, or feature requests to:
https://github.com/BRL-CAD/brlcad/issues
CONFIGURATION OPTIONS
---------------------
--- ENABLE_ALL ---
If set to ON, and the BRL-CAD configure process is managing the bext
dependencies, instructs bext to default to building local copies of the
dependencies it will enable per the BRL-CAD feature settings, rather than
searching for system versions.
--- BRLCAD_ENABLE_OPENGL ---
Enable support for OpenGL based Display Managers in BRL-CAD.
Default depends on whether OpenGL is successfully detected -
if it is, default is to enable.
Aliases: ENABLE_OPENGL
--- BRLCAD_X11_PROVIDER ---
Selects the X11 implementation used by BRL-CAD, Tk, Qt, and OpenGL. Accepted
values are AUTO, SYSTEM, and XMIN. AUTO is the default and deliberately
resolves to SYSTEM so installing Xmin cannot change an existing build.
XMIN selects an installed Xmin client SDK for deterministic GUI testing
without a host X server. The SDK must provide Xmin::ToolkitX11; OpenGL builds
also need Xmin::GL. Set Xmin_ROOT to the SDK installation prefix. Tk and Qt
must be built for the same provider because their public X11 APIs conceal
provider-private state; mixing Xmin and system client libraries is not ABI
safe and is rejected during configuration.
When BRL-CAD manages bext, it derives the matching bext SDK prefix from the
selected Xmin package. Bext then applies its version-matched Tk and Qt patches
automatically to whichever bundled toolkits are selected. No external patch
paths are needed.
A typical Xmin configuration is:
cmake .. -DBRLCAD_X11_PROVIDER=XMIN \
-DXmin_ROOT=/path/to/xmin-prefix
Bext retains advanced TK_EXTRA_PATCHES, TK_CONFIGURE_ARGS, QT_EXTRA_PATCHES,
and QT_XMIN_ROOT controls for custom profiles. The standard BRL-CAD Xmin
configuration does not need them. Refer to bext's Xmin profile documentation
before changing the bundled Tk or Qt revision.
--- BRLCAD_COMPONENTS ---
Semicolon separated list of components to enable for building - see
src/source_dirs.cmake for a list of the components that may be specified.
--- BRLCAD_ENABLE_RUNTIME_DEBUG ---
Enables support for application and library debugging facilities.
Disabling the run-time debugging facilities can provide a significant
(10%-30%) performance boost at the expense of extensive error
checking (that in turn help prevent corruption of your data).
Default is "ON", and should only be disabled for read-only render
work where performance is critical.
Aliases: ENABLE_RUNTIME_DEBUG, ENABLE_RUN_TIME_DEBUG, ENABLE_RUNTIME_DEBUGGING
ENABLE_RUN_TIME_DEBUGGING
--- BRLCAD_EXT_DIR ---
If specified, BRL-CAD will look in this directory for bext compiled outputs to
bundle and use during the build.
--- BRLCAD_EXT_SOURCE_DIR ---
If specified, BRL-CAD will look in this directory for bext source files. Use
this when you have a pre-existing bext clone and don't want BRL-CAD's configure
process to pull down another copy, but are still looking to have the BRL-CAD
configure process manage producing bext build outputs.
--- BRLCAD_EXT_PARALLEL ---
This number, when specified, describes how many compilation threads to use
when compiling bext sources. Default is 8.
--- BRLCAD_DEBUGGING ---
Add compiler flags to aid in program debugging. Defaults to ON.
Aliases: ENABLE_DEBUG, ENABLE_FLAGS_DEBUG, ENABLE_DEBUG_FLAGS
BRLCAD_FLAGS_DEBUG
--- BRLCAD_PGO ---
Enable profile-guided optimization build flags. Defaults to OFF.
Profile-guided optimization builds are possible via two-pass
compilation. Compile with this flag set, run the benchmark suite,
clean the build, and then compile again with this flag set. Supported
compilers will utilize data from the first pass to guide optimization,
typically resulting in a significant performance increase:
--- BRLCAD_WARNINGS ---
Use extra warning flags when compiling C/C++ code. Defaults to ON.
Aliases: ENABLE_WARNINGS, ENABLE_COMPILER_WARNINGS
BRLCAD_ENABLE_COMPILER_WARNINGS
--- BRLCAD_ENABLE_STRICT ---
Causes all compilation warnings for C code to be treated as errors. This is now
the default for BRL-CAD source code, and developers should address issues
discovered by these flags whenever possible rather than disabling strict
mode.
Aliases: ENABLE_STRICT, ENABLE_STRICT_COMPILE, ENABLE_STRICT_COMPILE_FLAGS
--- ENABLE_ALL_CXX_COMPILE ---
Build all C and C++ files with a C++ compiler. Defaults to OFF.
EXPERIMENTAL!
Aliases: ENABLE_ALL_CXX
--- BRLCAD_EXTRADOCS ---
The core option that enables and disables building of BRL-CAD's
AsciiDoc based documentation (includes manuals and man pages for
commands, among other things). It is built with BRL-CAD's bundled
asciiquack processor into HTML and man-page (troff) formats. Defaults
to ON for a full build and OFF for reduced target sets.
Aliases: ENABLE_DOCS, ENABLE_EXTRA_DOCS
+58
View File
@@ -0,0 +1,58 @@
Max OS X Installation Notes:
Being that this is the newest architecture to be added, there are some issues
to keep in mind with the installation when building from source. First, XFree86
will need to be installed if you want a gui. Mac OS X does not ship with an
X11 server installed by default. The XDarwin project, however, will include
the X11 libraries and headers necessary to properly build Tk (the only
component that presently "requires" X) and may be found at:
http://www.xdarwin.org
To build and install, you'll need to modify the Cakefile.defs file in the
source root. Modify the compilation options (near the top of the file)
as follows:
#define BUILD_OPTIMIZED 1
#define BUILD_SHARED 0
#define BUILD_XWINDOWS 1
#define BUILD_OPENGL 0
#define BUILD_PRODUCTION 1
There are details in the Cakefile.defs file for what each of these options
means, but the important one is that it is presently not possible to build
with shared libaries (patches welcome). Other than that the instructions
in INSTALL will all work with the exception of the "make install" step.
Run this instead:
cake install
If the build and install fails for whatever reason, then the system default Tcl
library is most likely getting in the way. You can temporarily move it out of
the way by doing:
sudo mv /usr/lib/libtcl.dylib /usr/lib/libtcl.dylib.backup
sudo mv /usr/lib/libtcl8.3.dylib /usr/lib/libtcl8.3.dylib.backup
sudo mv /usr/lib/libtclstub8.3.a /usr/lib/libtclstub8.3.a.backup
sudo mv /System/Library/Tcl /System/Library/Tcl.backup
Then you should be able to do:
sh setup.sh
cake clobber
cake
cake install
You can tell if a build succeeded properly by running "mged" from a terminal.
Also, you should be able to go into the "bench" directory and run the benchmark
(see doc/benchmark.doc) test script:
bench/try.sh
A window should pop up with a raytrace being displayed. If not, something is
not right. If you build without X support (setting in Cakefile.defs), then
you may verify your build by running "mged -c" or "bench/run.sh".
E-mail the cad list [cad@arl.army.mil] if any issues or questions arise.
Happy installation!
-3677
View File
File diff suppressed because it is too large Load Diff
+99
View File
@@ -0,0 +1,99 @@
#################################################################
# #
# Makefile #
# #
# The top-level Makefile for the BRL CAD Software Distribution #
# #
# This exists mostly as a convienience, so folks can #
# type "make install" and such like, and get the expected #
# results, even in the face of the rather complex mechanism. #
# Thus, we make Make into a simple front-end for gen.sh #
# #
# Author - #
# Michael John Muuss #
# #
# Source - #
# SECAD/VLD Computing Consortium, Bldg 394 #
# The U. S. Army Ballistic Research Laboratory #
# Aberdeen Proving Ground, Maryland 21005-5066 #
# #
# #
#################################################################
# SHELL = /bin/sh
# Main rule (default):
all:
-@sh gen.sh $@
help:
-@sh gen.sh $@
benchmark:
-@sh gen.sh $@
fast:
-@sh gen.sh $@
clean:
-@sh gen.sh $@
noprod:
-@sh gen.sh $@
clobber:
-@sh gen.sh $@
lint:
-@sh gen.sh $@
ls:
-@sh gen.sh $@
ls-bin:
-@sh gen.sh $@
depend:
-@sh gen.sh $@
install:
-@sh gen.sh $@
inst-nobak:
-@sh gen.sh $@
uninstall:
-@sh gen.sh $@
perms:
-@sh gen.sh $@
inst-man:
-@sh gen.sh $@
inst-dist:
-@sh gen.sh $@
print:
-@sh gen.sh $@
typeset:
-@sh gen.sh $@
nroff:
-@sh gen.sh $@
mkdir:
-@sh gen.sh $@
relink:
-@sh gen.sh $@
rmdir:
-@sh gen.sh $@
wc:
-@sh gen.sh $@
tclIndex:
-@sh gen.sh $@
tags:
-@sh gen.sh $@
TAGS:
-@sh gen.sh $@
etags:
-@sh gen.sh $@
command:
-@sh gen.sh $@
rcs-lock:
-@sh gen.sh $@
checkin:
-@sh gen.sh $@
dist:
-@sh gen.sh $@
arch:
-@sh gen.sh $@
pkg:
-@sh gen.sh $@
rpm:
-@sh gen.sh $@
sunpkg:
-@sh gen.sh $@
tcl:
-@sh gen.sh $@
+217
View File
@@ -0,0 +1,217 @@
#################################################################
# #
# Makefile.rules #
# #
# Author - #
# Michael John Muuss #
# #
# Source - #
# SECAD/VLD Computing Consortium, Bldg 394 #
# The U. S. Army Ballistic Research Laboratory #
# Aberdeen Proving Ground, Maryland 21005 #
# #
# $Header$ #
# #
#################################################################
# Define default list of targets to be made
all: ${PRODUCTS}
# Generic SCCS rule:
#.DEFAULT:
# $(GET) $(GFLAGS) -p s.$@ > $@
# touch $@
# This is how to make the product, but may not always apply (eg, libs).
# Also, this construct only works with the SysV make.
#${PRODUCTS}: $$@.o ${OBJS}
# $(CC) -o $@ ${LDFLAGS} $@.o ${OBJS} ${LIBES}
# size $@
# Format sources for printing on stdout.
# The invoker is responsible for diverting to their printer of choice.
print: ${MAKEFILE} ${HEADERS} ${CFILES} ${TFILES}
@pr ${MAKEFILE} ${HEADERS} ${CFILES} ${TFILES} *.${MANSECTION}
@nroff -Tlp -man *.${MANSECTION}
# Don't bother doing the stub pages
typeset:
${TYPESET_MAN1} *.${MANSECTION} ${TYPESET_MAN2}
lint: ${HEADERS} ${CFILES}
${LINT} ${LFLAGS} -I${INCDIR} ${CFILES} ${LLIBES} > ${SRCDIR}.lint
tags: ${HEADERS} ${CFILES}
ctags ${HEADERS} ${CFILES}
flow: ${HEADERS} ${CFILES}
cflow -I${INCDIR} ${CFILES} > ${SRCDIR}.flow
xref: ${HEADERS} ${CFILES}
cxref -c -s -w132 -I${INCDIR} ${CFILES} > ${SRCDIR}.xref
compare: all
for prod in ${PRODUCTS} ; \
do cmp ${BINDIR}/$$prod $$prod; \
done
uninstall: all
-@if test -n "${PRODUCTS}" ; \
then $(MAKE) $(MFLAGS) -$(MAKEFLAGS) uninst-prod ; \
fi
-@files=`echo *.${MANSECTION}` ; \
if test "$$files" != '*'.${MANSECTION} ; \
then $(MAKE) $(MFLAGS) -$(MAKEFLAGS) uninst-man ; \
fi
-@files=`echo *.${MANSECTION}.stub` ; \
if test "$$files" != '*'.${MANSECTION}.stub ; \
then $(MAKE) $(MFLAGS) -$(MAKEFLAGS) uninst-stub ; \
fi
uninst-prod:
-@for prod in ${PRODUCTS} ; \
do rm -f ${BINDIR}/$$prod ${BINDIR}/$$prod.bak 2>/dev/null; \
done
uninst-man:
-@for man in *.${MANSECTION} ; \
do rm -f ${MANDIR}${MANSECTION}/$$man \
${MANDIR}${MANSECTION}/$$man.bak 2>/dev/null ; \
done
uninst-stub:
-@for stub in *.${MANSECTION}.stub ; \
do man=`basename $$stub .stub`; \
rm -f ${MANDIR}${MANSECTION}/$$man \
${MANDIR}${MANSECTION}/$$man.bak 2>/dev/null ; \
done
# Handle all phases of final installation
install: all
-@if test -n "${PRODUCTS}" ; \
then $(MAKE) $(MFLAGS) -$(MAKEFLAGS) inst-prod ; \
fi
-@files=`echo *.${MANSECTION}` ; \
if test "$$files" != '*'.${MANSECTION} ; \
then $(MAKE) $(MFLAGS) -$(MAKEFLAGS) inst-man ; \
fi
-@files=`echo *.${MANSECTION}.stub` ; \
if test "$$files" != '*'.${MANSECTION}.stub ; \
then $(MAKE) $(MFLAGS) -$(MAKEFLAGS) inst-stub ; \
fi
-@sh -c "if test `${GETHOST}` = ${MASTERHOST} ; then $(MAKE) inst-dist; else exit 0 ; fi"
# Install all products
inst-prod: ${PRODUCTS}
-@for prod in ${PRODUCTS} ; \
do if cmp -s ${BINDIR}/$$prod $$prod; \
then echo $$prod unchanged; \
else mv -f ${BINDIR}/$$prod ${BINDIR}/$$prod.bak 2>/dev/null; \
${INS} $$prod ${BINDIR} && \
${AFTERINSTALL} ${BINDIR}/$$prod && \
echo "++++++INSTALLED" ${BINDIR}/$$prod && \
${AFTERINSTALL} ${BINDIR}/$$prod.bak && \
chmod ${BINPERM} ${BINDIR}/$$prod; \
fi \
done
# Install the actual manual pages
inst-man:
-@for man in *.${MANSECTION} ; \
do if cmp -s ${MANDIR}${MANSECTION}/$$man $$man; \
then echo $$man unchanged; \
else mv -f ${MANDIR}${MANSECTION}/$$man \
${MANDIR}${MANSECTION}/$$man.bak 2>/dev/null ; \
${INS} $$man ${MANDIR}${MANSECTION} && \
echo "++++++INSTALLED" ${MANDIR}${MANSECTION}/$$man && \
chmod ${MANPERM} ${MANDIR}${MANSECTION}/$$man; \
fi \
done
# Install the "stub" manual pages, which just source some other page
inst-stub:
-@for stub in *.${MANSECTION}.stub ; \
do man=`basename $$stub .stub`; \
if cmp -s ${MANDIR}${MANSECTION}/$$man $$stub; \
then echo $$man unchanged; \
else mv -f ${MANDIR}${MANSECTION}/$$man \
${MANDIR}${MANSECTION}/$$man.bak 2>/dev/null ; \
${INS} $$stub ${MANDIR}${MANSECTION}/$$man && \
echo "++++++INSTALLED" ${MANDIR}${MANSECTION}/$$man && \
chmod ${MANPERM} ${MANDIR}${MANSECTION}/$$man; \
fi \
done
# It might be better to say ${HEADERS} ${CFILES} ${SFILES},
# but that would miss routines that were not configured in a particular system.
inst-dist:
-rm -fr ${DISTRIBUTION}/${SRCDIR}/*
-${INS} ./Makefile.loc Makefile *.[hcfs] ${SHFILES} \
*.${MANSECTION} *.${MANSECTION}.stub \
*.doc \
${DISTRIBUTION}/${SRCDIR}/.
# running "make clobber" or "make clean noprod" will remove all binary files.
# "clean" is intended to remove .o files and by-products.
# "noprod" is intended to remove the final executables.
# Either can be used without the other, depending on the effect desired.
clobber: clean noprod
clean:
-rm -f core *~ *.o \
${SRCDIR}.out ${SRCDIR}.err ${SRCDIR}.xref \
${SRCDIR}.flow ${SRCDIR}.lint
noprod:
-rm -f ${PRODUCTS}
#
# Automaticly build #include dependencies.
#
# This code can't be simply replaced by the 4.3 BSD "cc -M".
#
# The convention for writing #include directives is:
# #include "./file" gives file in current directory
# #include "/file" gives file at absolute path
# #include "file" gives file in ${INCDIR}
# #include <file> leaves to CPP
#
# Note that there MUST be a SPACE after the "#include" in order to
# be seen; this allows conditional includes (if needed) to be indicated
# by a #include TAB, so as to not cause trouble.
depend:
-@if test -n "${CFILES}" ; \
then $(MAKE) $(MFLAGS) -$(MAKEFLAGS) do-depend ; \
fi
do-depend:
cd ../${SRCDIR}; \
mv -f Makefile.loc Makefile.bak; \
cp Makefile.bak Makefile.loc; \
chmod 664 Makefile.loc; \
for k in ${CFILES}; do \
i=`basename $$k .c`; \
echo $$i.o: ../${SRCDIR}/$$k >>makedep; \
grep '^#include ' /dev/null ../${SRCDIR}/$$k | sed \
-e 's,^../'${SRCDIR}'/,,' \
-e 's,c:[^"]*"\./\([^"]*\)".*,o: \1,' \
-e 's,c:[^"]*"/\([^"]*\)".*,o: /\1,' \
-e 's,c:[^"]*"\([^"]*\)".*,o: '${INCDIR}'/\1,' \
-e '/debug.h/d' \
-e '/c:[^<]*<\(.*\)>/d' \
>>makedep; \
echo ' $$(CC) $$(CFLAGS) -c ../'${SRCDIR}/$$k >>makedep; \
done; \
echo '# DO NOT DELETE THIS LINE -- make depend uses it' >>Makefile.loc; \
echo '# IF YOU PUT STUFF HERE IT WILL GO AWAY' >> Makefile.loc; \
echo '/^# DO NOT DELETE THIS LINE/+1,$$d' >eddep; \
echo '$$r makedep' >>eddep; \
echo 'w' >>eddep; \
ed - Makefile.loc < eddep; \
rm eddep makedep; \
echo '# DEPENDENCIES MUST END AT END OF FILE' >> Makefile.loc; \
echo '# IF YOU PUT STUFF HERE IT WILL GO AWAY' >> Makefile.loc; \
echo '# see make depend above' >> Makefile.loc
-3774
View File
File diff suppressed because it is too large Load Diff
+145 -182
View File
@@ -1,183 +1,146 @@
BRL-CAD
Release 7.44.2
http://brlcad.org/
BRL-CAD is a powerful cross-platform open source combinatorial
solid modeling system that includes an interactive 3D solid geometry
editor, a network-distributed symmetric multiprocessing (SMP)
high-performance ray-tracer with support for rendering and geometric
analysis, image and signal-processing tools, a system performance
analysis benchmark suite, a flexible geometry scripting interface,
and a high-performance geometric representation and analysis library.
TABLE OF CONTENTS
-----------------
Introduction
Table of Contents
Getting Started
Compile and Install
Benchmark
Communication
Bug Reports/Feature Requests
Distribution Details
Background Information
GETTING STARTED
---------------
This README file exists only to provide you a brief roadmap to the
contents of the BRL-CAD distribution.
Some platforms have additional platform-specific documentation that
should be consulted after reading this file:
doc/README.Windows -- Microsoft Windows
doc/README.MacOSX -- Apple Mac OS X
doc/README.Linux -- Various Linux distributions
doc/README.* -- Other platforms, e.g., BSD, VAX
Information on how to install and run the software, to get involved
with development, or to run the performance benchmark test suite are
covered in detail in separate standalone documents. For more details
on what BRL-CAD provides, consult the main website.
Information relevant to the source code is contained in the HACKING
(developer guide) and COPYING (legal overview) files.
Note that only sample geometry models are included in public
distributions of BRL-CAD. Detailed models are only available through
official U.S. Gov't channels, e.g., via Advanced Joint Effectiveness
Model (AJEM) support.
COMPILE AND INSTALL
-------------------
In order to compile and install BRL-CAD from a source distribution,
the latest CMake ( http://www.cmake.org ), a recent compiler, and at
least 3GB of disk space are recommended. More details are available
at https://brlcad.org/wiki/Compiling
Typically, the following steps should result in a successful install:
tar -xvzf brlcad-VERSION.tar.gz
mkdir brlcad-VERSION/build
cd brlcad-VERSION/build
cmake .. -DBRLCAD_ENABLE_STRICT=OFF -DCMAKE_BUILD_TYPE=Release
make -j4
make install
See the included INSTALL text file for explanation of the various
cmake configuration options available for building BRL-CAD.
BENCHMARK
---------
After the build successfully completes, you will be able to verify
basic functionality by running the BRL-CAD Benchmark. Running the
benchmark suite is integrated into the build system such that any time
after running CMake (in the cmake gui, configure and generate must both
be performed) you may run:
make benchmark
If the build is successful, you will see "CORRECT" numbers and a
performance summary at the end. The "vgr" line effectively shows you
approximately how much faster your machine is to a VAX 11/780. After
installing BRL-CAD, you may run the 'benchmark' tool as well to run
the BRL-CAD Benchmark.
See the paper in doc/benchmark.tr for information on analyzing and
comparing the results of the benchmark tests in more detail.
COMMUNICATION
-------------
There are various BRL-CAD mailing lists available including three
developer-oriented lists, a user list, and a read-only news
announcement list:
http://sourceforge.net/mail/?group_id=105292
For interactive discussion, please join our Zulip chat:
https://brlcad.zulipchat.com
BUG REPORTS AND FEATURE REQUESTS
--------------------------------
Please submit all bugs, support requests, and feature requests to:
https://github.com/BRL-CAD/brlcad/issues
DISTRIBUTION DETAILS
--------------------
BRL-CAD releases are available at:
https://github.com/BRL-CAD/brlcad/releases
Assets stored for each release will always include source archives,
and usually binary compilations for commonly used operating systems.
For developers, BRL-CAD is available via Git version control cloning:
https://github.com/BRL-CAD/brlcad
BACKGROUND INFORMATION
----------------------
BRL-CAD is the primary tri-service solid modeling CAD system used by
the U.S. military to model weapons systems for vulnerability and
lethality analyses. The solid modeling system is frequently used in a
wide range of military and industrial application including in the
design and analysis of vehicles, mechanical parts, and architecture.
The package has also been used in radiation dose planning, medical
visualization, computer graphics education, CSG concepts and modeling
education, and system performance benchmark testing among other
purposes.
Actively developed since 1979, BRL-CAD is a collection of more than
400 tools, utilities, and applications comprising more than a million
lines of source code. BRL-CAD supports a great variety of geometric
representations including an extensive set of traditional CSG
primitive implicit solids such as boxes, ellipsoids, cones, and tori,
as well as explicit solids made from closed collections of Uniform
B-Spline Surfaces, Non-Uniform Rational B-Spline (NURBS) surfaces,
n-Manifold Geometry (NMG), and purely faceted mesh geometry. All
geometric objects may be combined using boolean set-theoretic CSG
operations including union, intersection, and difference.
BRL-CAD has been under active development for more than 20 years with
a portability heritage that includes systems such as a DEC VAX-11/780
running 4.3 BSD; DECStations running ULTRIX; Silicon Graphics 3030, 4D
"IRIS", O2, Onyx, and Origin systems running various versions of IRIX;
Sun Microsystems Sun-3 and Sun-4 Sparcs running SunOS; the Cray 1,
Cray X-MP, Cray Y-MP, and Cray 2 running UNICOS; DEC Alpha AXP running
OSF/1; Apple Macintosh II running A/UX; iPSC/860 Hypercube running
NX/2; the Alliant FX/8, FX/80, and FX/2800; Gould/Encore SEL PowerNode
6000/9000 and NP1; NeXT workstations; IBM RS/6000; HPPA 9000/700
running HPUX; Ardent/Stardent; Encore Multi-Max; and much much more.
BRL-CAD's extensive portability of course also includes a plethora of
common desktop and server versions of BSD, IRIX, Solaris, Mac OS X,
Linux, and Windows.
The BRL-CAD package is intentionally designed to be extensively
cross-platform and is actively developed on and maintained for many
common operating system environments including various BSD
distributions, Linux, Solaris, Mac OS X, and Windows. The entire
package is distributed in binary and source code form as free open
source software (FOSS), provided under Open Source Initiative (OSI)
approved license terms. BRL-CAD was released as open source in
December 2004. See the COPYING file for more details.
.\" $Header$
.\" groff -ms README | print-postscript
.TL
README
.sp
The BRL-CAD Package
.br
Release 6.0
.br
(October-2002)
.RT
.IP "VERSION"
.sp
This document is printed from the README file in the BRL-CAD distribution.
The version in the printed manuals are usually somewhat older
than the version on the actual distribution tape.
When attempting to
install the software, please refer to the documentation
versions actually contained on the distribution tape.
.sp
.IP CONTENTS
.sp
This README file exists only to provide you a brief roadmap to
the contents of the BRL-CAD distribution.
The information on how to install and operate the software,
and perform the benchmark tests have become sufficiently large
that they are now each a standalone document.
.sp
Please note that
this distribution package does \fInot\fR include
the various military-specific model
analysis tools such as MUVES, GIFT, SAR, SLAVE, VAST, etc., nor does it
include any military databases.
If you desire to have access to this material,
please contact Sean Morrison at (410)-278-6678.
.sp
.IP "INSTALLATION"
.sp
To install the BRL-CAD Package see the instructions in doc/install.doc.
This file includes directions on the best way to get started with the
distribution, as well as details on how to configure and install the
software. This file also includes directions on how to compile and run
the benchmark tests.
.sp
.IP "BENCHMARK"
.sp
See the paper in doc/benchmark.doc for information on
analyzing the results of the benchmark tests.
Comparisons between various different computers are listed.
.sp
.IP "BACKGROUND MATERIAL"
.sp
For overview information on the whole package, consult
the overview paper in the file papers/overview, and
the brlcad(1) manual page in the file util/brlcad.1.
For a discussion of the significance of this software,
read the paper "Understanding the Preparation and Analysis of Solid
Models", included in the file papers/solid-models.
.sp
.IP "DISTRIBUTION DETAILS"
.sp
This software is governed by a limited distribution agreement.
To obtain a copy of the BRL-CAD Package distribution materials, there
are two options:
.sp
1. Free distribution with no support privileges: Those users with
online access to the InterNet may obtain the BRL-CAD Package via
FTP file transfer, at no cost, after completing and returning a signed
copy of the printed distribution agreement. A blank agreement form is
available only via anonymous FTP from host ftp.arl.army.mil (address
192.12.65.24) from file "brl-cad/agreement". No installation
assistance or telephone support will be available.
.sp
2. Full service distribution: The Survivability/Vulnerability
Information Analysis Center (SURVIAC) administers the supported BRL-CAD
distributions and information exchange programs for ARL. Full service
distributions a copy of the full distribution materials on your choice
of magnetic tape media, or you may elect to obtain your copy via FTP.
One printed set of BRL-CAD documentation will be mailed to you.
Software upgrades will be provided at no additional charge,
and you will have access to full technical assistance by phone, FAX,
letter, or E-mail. Agencies of the Federal Government may acquire the
full service distribution with a simple MIPR or OGA funds transfer.
.sp
.nf
For further details, contact:
.sp .5
BRL-CAD Distribution
SURVIAC Aberdeen Satellite Office
4695 Millennium Drive
Belcamp, MD 210017-1505 USA
.fi
.sp .5
or call USA telephone (410)-273-7794, send
E-mail to <cad-dist@arl.army.mil>, FAX your letter to USA (410)-272-6763,
or write to the above address.
.fi
.sp
.ne 1i
.IP "COMMUNICATION"
.sp
You are invited to participate in the InterNet (aka "ARPANET")
electronic mailing list on the BRL-CAD software, which is called
.sp .5
.ti +1i
<CAD @ ARL.ARMY.MIL>.
.sp .5
Bug reports and discussions of new features
are the main topics; volume of messages has been light (so far).
Direct your bug reports to this address. Request a subscription by
sending to
.sp .5
.ti +1i
<CAD-REQUEST @ ARL.ARMY.MIL>.
.sp .5
If you find bugs, please report your experiences via E-mail.
.sp
A variety of information on BRL-CAD is available via the World-Wide-Web.
Papers, documentation, and the software repository may be found at
.sp .5
.ti +1i
http://ftp.arl.army.mil/brlcad/
.sp
.IP "FUTURE EVENTS"
.sp
It is expected that new releases of this software will be issued
between once and twice a year.
Information about new releases will be routinely provided
by both paper and electronic mail
to recipients of this software.
If your address changes, please let us
know, so we can update our records.
.sp
.KS
.nf
Best Wishes,
The BRL-CAD Development Team
devs@brlcad.org
-Lee Butler
.sp
Leader, Advanced Computer Systems Team
AMSRL-SL-BE
U.S. Army Research Laboratory
APG, MD 21005-5068 USA
.sp
E-mail: <BUTLER @ ARL.ARMY.MIL>
.KE
.fi
-2726
View File
File diff suppressed because it is too large Load Diff
+69
View File
@@ -0,0 +1,69 @@
/*
* tab/Cakefile
*/
#define SRCDIR anim
#define PRODUCTS anim_cascade anim_fly anim_hardtrack anim_keyread \
anim_lookat anim_offset anim_orient anim_script \
anim_sort anim_time anim_track anim_turn chan_add \
chan_mult chan_permute \
#define SRCSUFF .c
#define MANSECTION 1
#include "../Cakefile.defs"
#include "../Cakefile.prog"
#define FILES anim_cascade anim_fly anim_hardtrack anim_keyread \
anim_lookat anim_offset anim_orient anim_script anim_sort \
anim-time anim_track anim_turn cattrack chan_add chan_mult \
chan_permute
/* Explicit composition of each product */
anim_cascade: anim_cascade.o LIBBN_DEP LIBBU_DEP
CC LDFLAGS anim_cascade.o LIBRT LIBBN LIBBU LIBBU_LIBES LIBES -o anim_cascade
anim_fly: anim_fly.o LIBBU_DEP
CC LDFLAGS anim_fly.o LIBBU LIBBU_LIBES LIBES -o anim_fly
anim_hardtrack: anim_hardtrack.o LIBBN_DEP LIBBU_DEP
CC LDFLAGS anim_hardtrack.o LIBRT LIBBN LIBBU LIBBU_LIBES LIBES -o anim_hardtrack
anim_keyread: anim_keyread.o LIBBN_DEP LIBBU_DEP
CC LDFLAGS anim_keyread.o LIBBN LIBBU LIBBU_LIBES LIBES -o anim_keyread
anim_lookat: anim_lookat.o LIBBN_DEP LIBBU_DEP
CC LDFLAGS anim_lookat.o LIBBN LIBBU LIBBU_LIBES LIBES -o anim_lookat
anim_offset: anim_offset.o LIBBN_DEP LIBBU_DEP
CC LDFLAGS anim_offset.o LIBBN LIBBU LIBBU_LIBES LIBES -o anim_offset
anim_orient: anim_orient.o LIBBN_DEP LIBBU_DEP
CC LDFLAGS anim_orient.o LIBRT LIBBN LIBBU LIBBU_LIBES LIBES -o anim_orient
anim_script: anim_script.o LIBBN_DEP LIBBU_DEP
CC LDFLAGS anim_script.o LIBRT LIBBN LIBBU LIBBU_LIBES LIBES -o anim_script
anim_sort: anim_sort.o LIBBU_DEP
CC LDFLAGS anim_sort.o LIBBU LIBBU_LIBES LIBES -o anim_sort
anim_time: anim_time.o
CC LDFLAGS anim_time.o LIBRT LIBBN LIBBU LIBBU_LIBES LIBES -o anim_time
anim_track: anim_track.o cattrack.o LIBBN_DEP LIBBU_DEP
CC LDFLAGS anim_track.o cattrack.o LIBRT LIBBN LIBBU LIBBU_LIBES LIBES -o anim_track
anim_turn: anim_turn.o LIBBN_DEP LIBBU_DEP
CC LDFLAGS anim_turn.o LIBRT LIBBN LIBBU LIBBU_LIBES LIBES -o anim_turn
chan_add: chan_add.o
CC LDFLAGS chan_add.o LIBES -o chan_add
chan_mult: chan_mult.o
CC LDFLAGS chan_mult.o LIBES -o chan_mult
chan_permute: chan_permute.o
CC LDFLAGS chan_permute.o LIBES -o chan_permute
#include "../Cakefile.rules"
+187
View File
@@ -0,0 +1,187 @@
.TH ANIM_CASCADE 1 BRL/CAD
.SH NAME
anim_cascade - evaluate movement of an object relative to a moving frame of
reference
.SH SYNOPSIS
.B anim_cascade [-s][-o(f|r|a)] [-(f|r|a)(c|y) # # #] <
.B input.table >
.B output.table
.SH DESCRIPTION
.I Anim_cascade
is designed to enable the user to control the movement of objects relative to
other objects. In the normal mode of operation, the user supplies
the position and orientation of a (possibly moving) frame of reference and
the position
and orientation of an object relative to the frame of reference,
and
.I anim_cascade
produces the absolute position and orientation of the object at each
point in time.
All orientations are specified as yaw, pitch, and roll.
The columns of the input table are:
.sp
time fx fy fz fyaw fpitch froll rx ry rz ryaw rpitch rroll
.sp
and the columns of the output table are:
.sp
time ax ay az ayaw apitch aroll
.sp
Here "f" refers to the frame of reference, "r" refers to the position
and orientation of the object relative to the frame, and "a"
refers to the absolute position and orientation of the object.
.SH OPTIONS
.TP
.B \-or
Output the relative position and orientation.
If this option is specified,
.I anim_cascade
will expect the absolute position and orientation of the frame of
reference and the object as input,
and will produce the position and orientation or the object relative to
the frame as output. The
input columns should be:
.sp
time fx fy fz fyaw fpitch froll ax ay az ayaw apitch aroll
.sp
and the output columns will be:
.sp
time rx ry rz ryaw rpitch rroll
.sp
.TP
.B \-of
Output the frame of reference.
If this option is specified,
.I anim_cascade
will expect the absolute and relative positions and orientations of the
object as input,
and will produce the corresponding frame of reference as output.
The input columns should be:
.sp
time ax ay az ayaw apitch aroll rx ry rz ryaw rpitch rroll
.sp
and the output columns will be:
.sp
time fx fy fz fyaw fpitch froll
.sp
.TP
.B \-fc # # #
Specify a constant position for the frame of reference. The
columns fx, fy, and fz should be omitted from the input table, and the
command-line arguments will be used instead.
This has no effect if used
in conjunction with
.B -of
.TP
.B \-fy # # #
Specify a constant orientation for the frame of reference. The
columns fyaw, fpitch, and froll should be omitted from the input table,
and the command-line arguments will be used instead.
This has no effect if used
in conjunction with
.BR -of .
.TP
.B \-rc # # #
Specify a constant position of the object relative to the frame
of reference. The
columns rx, ry, and rz should be omitted from the input table, and the
command-line arguments will be used instead.
This has no effect if used
in conjunction with
.BR -or .
.TP
.B \-ry # # #
Specify a constant orientation of the object relative to the
frame of reference. The
columns ryaw, rpitch, and rroll should be omitted from the input table,
and the command-line arguments will be used instead.
This has no effect if used
in conjunction with
.BR -or .
.TP
.B \-ac # # #
Specify a constant absolute position for the object. The
columns ax, ay, and az should be omitted from the input table, and the
command-line arguments will be used instead.
This has no effect unless used
in conjunction with
.B -or
or
.BR -of .
.TP
.B \-ay # # #
Specify a constant absolute orientation for the object. The
columns ayaw, apitch, and aroll should be omitted from the input table,
and the
command-line arguments will be used instead.
This has no effect unless used
in conjunction with
.B -or
or
.BR -of .
.TP
.B \-s
Suppress time column. No time column is read or written.
.sp
Note: When all of the input columns are specified with command-line arguments,
then standard input is not read and
only one line of output is produced. The time value will be set to zero,
unless it is suppressed.
.SH EXAMPLES
1. Suppose that you want the virtual camera to pan in a circle around a
moving vehicle, always staying a fixed distance from the vehicle.
There should already exist an animation table with the time, position,
and orientation of the vehicle in each frame. This will be the moving
frame of reference. Next, you should create an animation table which
describes how the camera would need to move if the vehicle stood still
at the origin. The columns of the second animation table should be
appended to the columns of the first table
(using
.IR paste ,
for example), to create the
input table.
.I Anim_cascade
will produce an absolute animation table for
the camera, suitable to use as input to
.IR anim_script :
.sp
anim_cascade < input.table | anim_script -v500 > view.script
.sp
2. Suppose that you have an animation path for an object and you want to
know when it crosses a given oblique plane. You can use the
.B -or
option to
find out what the position of the object is relative to the frame of
reference of the plane. Suppose that the plane is defined by the
equation:
.sp
x + z = 0
.sp
In a frame of reference located at the origin with a pitch of 45
degrees, the x-axis is perpendicular to the given plane.
To convert the absolute animation path into this frame of reference, the command
would be:
.sp
anim_cascade -or -fc 0 0 0 -fy 0 45 0 < absolute.table > relative.table
.sp
Wherever the x coordinate in the output table is positive, the object
lies above the plane.
.sp
3. Suppose that one object is situated at the point (1,2,3) with a yaw,
pitch, and roll of (45, 25, 10). Suppose further that you want to
position a camera so that to the camera, the first object seems to be 10
units straight ahead, facing to the right. You could find the required
position and orientation of the camera with the following command:
.sp
anim_cascade -s -of -ac 1 2 3 -ay 45 25 10 -rc 10 0 0 -ry -90 0 0
.sp
.SH AUTHOR
Carl J. Nuzman
.SH COPYRIGHT
This software is Copyright (C) 1993-2004 by the United States Army
in all countries except the USA. All rights reserved.
.SH "BUG REPORTS"
Reports of bugs or problems should be submitted via electronic
mail to <CAD@ARL.ARMY.MIL>.
+301
View File
@@ -0,0 +1,301 @@
/* A N I M _ C A S C A D E . C
*
* Purpose: Given position and orientation of main frame of reference,
* along with the position and orientation of another frame with respect
* to the main frame, give the absolute orientation and position of the
* second frame.
* For example, given the position and orientation of a tank, and of the
* turret relative to the tank, you can get the absolute position and
* orientation of the turret at each time.
* Or, optionally, given position and orientation of main frame of
* reference, and the absolute position and orientation of another frame,
* find the position and orientation of the second frame in terms of the main
* frame of reference. (-i option).
*
* Usage:
* anim_cascade main.table < relative.table > absolute.table
*
* The format of the tables is:
* time x y z yaw pitch roll
* unless specified otherwise by options.
*
* Author -
* Carl J. Nuzman
*
* Source -
* The U. S. Army Research Laboratory
* Aberdeen Proving Ground, Maryland 21005-5068 USA
*
* Distribution Notice -
* Re-distribution of this software is restricted, as described in
* your "Statement of Terms and Conditions for the Release of
* The BRL-CAD Pacakge" agreement.
*
* Copyright Notice -
* This software is Copyright (C) 1993-2004 by the United States Army
* in all countries except the USA. All rights reserved.
*/
#include "conf.h"
#include <math.h>
#include <stdio.h>
#include "machine.h"
#include "vmath.h"
#include "bu.h"
#include "bn.h"
#include "anim.h"
#ifndef M_PI
#define M_PI 3.14159265358979323846
#endif
#ifndef M_PI
#define RTOD 180.000/M_PI
#endif
#define CASCADE_A 0
#define CASCADE_R 1
#define CASCADE_F 2
int get_args();
extern void anim_dy_p_r2mat();
extern void anim_tran();
extern int anim_mat2ypr();
extern int bu_optind;
extern char *bu_optarg;
vect_t fcenter, fypr, rcenter, rypr, acenter, aypr;
int cmd_fcen, cmd_fypr, cmd_rcen, cmd_rypr, cmd_acen, cmd_aypr;
int output_mode, read_time, print_time;
int
main (argc,argv)
int argc;
char **argv;
{
int val;
fastf_t time, yaw1, pitch1, roll1, yaw2, pitch2, roll2;
vect_t cen1, cen2, cen_ans, ang_ans, rad_ang_ans, rotated;
mat_t m_rot1, m_rot2, m_ans;
int one_time, read_cen1, read_cen2, read_rot1, read_rot2;
read_cen1 = read_cen2 = read_rot1 = read_rot2 = 1;
if (!get_args(argc,argv))
fprintf(stderr,"anim_cascade: Argument error.");
switch (output_mode) {
case CASCADE_A:
if (cmd_fcen) {
VMOVE(cen1, fcenter);
read_cen1 = 0;
}
if (cmd_rcen) {
VMOVE(cen2, rcenter);
read_cen2 = 0;
}
if (cmd_fypr){
anim_dy_p_r2mat(m_rot1, fypr[0], fypr[1], fypr[2]);
read_rot1 = 0;
}
if (cmd_rypr){
anim_dy_p_r2mat(m_rot2, rypr[0], rypr[1], rypr[2]);
read_rot2 = 0;
}
break;
case CASCADE_R:
if (cmd_fcen) {
VMOVE(cen1, fcenter);
read_cen1 = 0;
}
if (cmd_acen) {
VMOVE(cen2, acenter);
read_cen2 = 0;
}
if (cmd_fypr){
anim_dy_p_r2mat(m_rot1, fypr[0], fypr[1], fypr[2]);
read_rot1 = 0;
}
if (cmd_aypr){
anim_dy_p_r2mat(m_rot2, aypr[0], aypr[1], aypr[2]);
read_rot2 = 0;
}
break;
case CASCADE_F:
if (cmd_acen) {
VMOVE(cen1, acenter);
read_cen1 = 0;
}
if (cmd_rcen) {
VMOVE(cen2, rcenter);
read_cen2 = 0;
}
if (cmd_aypr){
anim_dy_p_r2mat(m_rot1, aypr[0], aypr[1], aypr[2]);
read_rot1 = 0;
}
if (cmd_rypr){
anim_dy_p_r2mat(m_rot2, rypr[0], rypr[1], rypr[2]);
read_rot2 = 0;
}
break;
default:
break;
}
one_time = (!(read_cen1||read_cen2||read_rot1||read_rot2));
read_time = one_time ? 0 : print_time;
time = 0.0;
val = 3;
while(1){
if (read_time) {
val=scanf("%lf",&time);
if (val < 1) break;
}
if (read_cen1)
val =scanf("%lf %lf %lf",cen1, cen1+1, cen1+2);
if (read_rot1) {
val=scanf("%lf %lf %lf", &yaw1, &pitch1, &roll1);
anim_dy_p_r2mat(m_rot1, yaw1, pitch1, roll1);
}
if (read_cen2) {
val=scanf("%lf %lf %lf", cen2, cen2+1,cen2+2);
}
if (read_rot2) {
val=scanf("%lf %lf %lf", &yaw2, &pitch2, &roll2);
anim_dy_p_r2mat(m_rot2, yaw2, pitch2, roll2);
}
if (val<3) break;
if (output_mode==CASCADE_R) {
anim_tran(m_rot1);
VSUB2(rotated,cen2,cen1);
MAT4X3PNT(cen_ans, m_rot1, rotated);
bn_mat_mul(m_ans, m_rot1, m_rot2);
} else if (output_mode==CASCADE_F) {
anim_tran(m_rot2);
bn_mat_mul(m_ans, m_rot1, m_rot2);
MAT4X3PNT(rotated, m_ans, cen2);
VSUB2(cen_ans, cen1, rotated);
} else {
MAT4X3PNT(rotated, m_rot1, cen2);
VADD2(cen_ans, rotated, cen1);
bn_mat_mul(m_ans, m_rot1, m_rot2);
}
anim_mat2ypr(rad_ang_ans, m_ans);
VSCALE(ang_ans, rad_ang_ans, RTOD);
if (print_time){
printf("%g",time);
}
printf("\t%.12g\t%.12g\t%.12g", cen_ans[0], cen_ans[1], cen_ans[2]);
printf("\t%.12g\t%.12g\t%.12g", ang_ans[0], ang_ans[1], ang_ans[2]);
printf("\n");
if (one_time) break;
}
return( 0 );
}
#define OPT_STR "so:f:r:a:"
int get_args(argc,argv)
int argc;
char **argv;
{
int c,d;
output_mode = CASCADE_A;
cmd_fcen = cmd_fypr = cmd_rcen = cmd_rypr = cmd_acen = cmd_aypr = 0;
print_time = 1;
while ( (c=bu_getopt(argc,argv,OPT_STR)) != EOF) {
switch(c){
case 'f':
d = *(bu_optarg);
if (d == 'c'){
sscanf(argv[bu_optind],"%lf",fcenter+0);
sscanf(argv[bu_optind+1],"%lf",fcenter+1);
sscanf(argv[bu_optind+2],"%lf",fcenter+2);
bu_optind += 3;
cmd_fcen = 1;
break;
} else if ( d =='y'){
sscanf(argv[bu_optind],"%lf",fypr+0);
sscanf(argv[bu_optind+1],"%lf",fypr+1);
sscanf(argv[bu_optind+2],"%lf",fypr+2);
bu_optind += 3;
cmd_fypr = 1;
break;
} else {
fprintf(stderr,"anim_cascade: unknown option -f%c\n", d);
}
break;
case 'r':
d = *(bu_optarg);
if (d == 'c'){
sscanf(argv[bu_optind],"%lf",rcenter+0);
sscanf(argv[bu_optind+1],"%lf",rcenter+1);
sscanf(argv[bu_optind+2],"%lf",rcenter+2);
bu_optind += 3;
cmd_rcen = 1;
break;
} else if ( d =='y'){
sscanf(argv[bu_optind],"%lf",rypr+0);
sscanf(argv[bu_optind+1],"%lf",rypr+1);
sscanf(argv[bu_optind+2],"%lf",rypr+2);
bu_optind += 3;
cmd_rypr = 1;
break;
} else {
fprintf(stderr,"anim_cascade: unknown option -r%c\n", d);
}
break;
case 'a':
d = *(bu_optarg);
if (d == 'c'){
sscanf(argv[bu_optind],"%lf",acenter+0);
sscanf(argv[bu_optind+1],"%lf",acenter+1);
sscanf(argv[bu_optind+2],"%lf",acenter+2);
bu_optind += 3;
cmd_acen = 1;
break;
} else if ( d =='y'){
sscanf(argv[bu_optind],"%lf",aypr+0);
sscanf(argv[bu_optind+1],"%lf",aypr+1);
sscanf(argv[bu_optind+2],"%lf",aypr+2);
bu_optind += 3;
cmd_aypr = 1;
break;
} else {
fprintf(stderr,"anim_cascade: unknown option -a%c\n", d);
}
break;
case 'o':
d = *(bu_optarg);
if (d == 'r'){
output_mode = CASCADE_R;
} else if (d == 'f') {
output_mode = CASCADE_F;
} else if (d == 'a') { /* default */
output_mode = CASCADE_A;
} else {
fprintf(stderr,"anim_cascade: unknown option -i%c\n",d);
}
break;
case 's':
print_time = 0;
break;
default:
fprintf(stderr,"anim_cascade: unknown option: -%c\n",c);
return(0);
}
}
return(1);
}
+94
View File
@@ -0,0 +1,94 @@
.TH ANIM_FLY 1 BRL/CAD
.SH NAME
anim_fly - make animation table to simulate flying motion
.SH SYNOPSIS
.B anim_fly
.B [-f factor]
.B [-r]
.B [-p integer]
.B [-b max_bank_angle]
.B [-s step]
.B < in.table
.B > out.table
.SH DESCRIPTION
This filter is designed to simulate the motion of an airplane.
Given a four-column table specifying the desired 3D position of the
airplane at each relevant time step,
.I anim_fly
produces a seven-column file
which also includes the orientation of the plane in terms of yaw,
pitch, and roll. The yaw and pitch are manipulated so that
the plane faces the direction of motion, while the roll is used to do
banking.
.SH OPTIONS
.TP
.B -f#
This option specifies a factor to control the severity of the banking.
The best factor is a subjective decision; a good starting point can best
be obtained by using the -b option. Animations representing aircraft
of different scales will need different factors.
If the
slightest curve throws the plane into a 90 degree bank, the factor is
too large; if it doesn't bank enough, the factor is too small. The size
of the best factor varies inversely with the size of the imagined
aircraft plane.
If a factor of 0 is used, there will
be no banking. This would be appropriate for animating a ground
vehicle.
.TP
.B -b#
This option is used to estimate a good value for the -f option. The
parameter is the maximum desired banking angle. Anim_fly then computes
the factor necessary to keep the banking below the specified angle. This
value is returned instead of anim_fly's usual output.
.TP
.B -r
Suppress vertical loop smoothing.
A special case occurs if the aircraft is to perform a vertical
loop. Normally, the algorithm likes to keep the aircraft right-side up.
This would cause the airplane to do an instantaneous 180 roll as it hits
the vertical portion of the loop. To counter this, a capability was
built in which prevents this sudden roll, allowing the aircraft to go
upside-down in a loop situation. This feature can be suppressed with the
.B -r
flag.
.TP
.B -p
Specify the ratio of input rows to output rows, which must be
an integer. The default, of course, is one. The accuracy of the output
depends on having a large number of input lines, which is not usually a
problem in animations, which require a large number of frames per
second, anyway. If a test animation with a small number of frames per
second is being created, the user should still use an input table
with a high number of input rows, reducing the frequency of the output
with the
.B -p
option. For example, if
.B in.table
contains 30 rows for each
second of the animation, then the command:
.sp
anim_fly -f0.001 -p10 < in.table > out.table
.sp
would produce an animation table containing 3 rows for each
second of the animation.
.TP
.B -s
Specify the minimum step size for the discrete-time differentiation. At any
given point on the flight path, the yaw, pitch, and roll are calculated based
on a past point, the current point, and a future point. Normally,
these are consecutive points from the input table. If the time
difference between the points falls below a certain threshold,
then non-consecutive points are used to avoid
numerical instability. The default time threshhold is 0.1 seconds - this
can be raised or lowered using the -s option.
Try raising the threshold if the output orientations experience random
jiter.
.SH AUTHOR
Carl J. Nuzman
.SH COPYRIGHT
This software is Copyright (C) 1993-2004 by the United States Army
in all countries except the USA. All rights reserved.
.SH "BUG REPORTS"
Reports of bugs or problems should be submitted via electronic
mail to <CAD@ARL.ARMY.MIL>.
+320
View File
@@ -0,0 +1,320 @@
/* A N I M _ F L Y . C
*
* Simulate flying motion, for an airplane or virtual camera.
*
* This filter operates on animation tables. Given the desired position
* of the airplane in each frame, anim_fly produces a table including the
* plane's position and orientation. A "magic factor" should be supplied
* to control the severity of banking. Looping behavior can be toggled
* with another option.
*
*
* Author -
* Carl J. Nuzman
*
* Source -
* The U. S. Army Research Laboratory
* Aberdeen Proving Ground, Maryland 21005-5068 USA
*
* Distribution Notice -
* Re-distribution of this software is restricted, as described in
* your "Statement of Terms and Conditions for the Release of
* The BRL-CAD Pacakge" agreement.
*
* Copyright Notice -
* This software is Copyright (C) 1993-2004 by the United States Army
* in all countries except the USA. All rights reserved.
*/
#include "conf.h"
#include <math.h>
#include <stdio.h>
#include "machine.h"
#include "externs.h"
#include "bu.h"
#include "vmath.h"
#include "anim.h"
#ifndef M_PI
#define M_PI 3.14159265358979323846
#endif
#define MAXN 100
int estimate_f = 0;
fastf_t max_bank = 0;
fastf_t max_cross = 0;
int loop = 1;
int print_int = 1;
fastf_t magic_factor = 1.0;
fastf_t desired_step = 0.1;
int get_args();
#define PREP -1
#define START 0
#define MIDDLE 1
#define WANE 2
#define END 3
#define STOP 4
int
main(argc,argv)
int argc;
char **argv;
{
int count, status, num_read, enn, i, pp;
fastf_t *points, *cur;
fastf_t yaw, pch, rll, stepsize, first[4], second[4];
fastf_t f_prm_0(), f_prm_1(), f_prm_2();
void get_orientation();
yaw = pch = rll = 0.0;
if (!get_args(argc,argv))
fprintf(stderr,"Anim_fly: Get_args error");
/* read first two lines of table to determine the time step used */
/* (a constant time step is assumed throughout the rest of the file)*/
scanf("%lf %lf %lf %lf", first, first+1, first+2, first+3);
scanf("%lf %lf %lf %lf", second, second+1, second+2, second+3);
stepsize = second[0]-first[0];
/* determine n, the number of points to store ahead and behind
* the current point. 2n points are stored, minimum enn=2 */
enn = (int) (desired_step/stepsize);
if (enn>MAXN) enn=MAXN;
if (enn<1) enn=1;
/* allocate storage */
points = (fastf_t *) calloc((3*enn+1)*4, sizeof(fastf_t));
/* read the first 3n points into the storage array*/
VMOVEN(points+4, first, 4);
VMOVEN(points+8, second, 4);
num_read=4; /* in order to pass test if n=1 */
for (cur=points+12; cur<points+(4*(3*enn+1)); cur+=4){
num_read=scanf("%lf %lf %lf %lf", cur,cur+1,cur+2,cur+3);
}
if (num_read<4){
fprintf(stderr,"Anim_fly: Not enough lines in input table.\n");
fprintf(stderr,"Increase number of lines or reduce the minimum stepsize with -s.\n");
fprintf(stderr,"Currently the minumum step size is %g seconds.\n",desired_step);
exit(0);
}
max_cross = 0;
count = 0;
pp = 0;
status = START;
while (status != STOP) {
switch (status) {
case START: /* first n points */
pp += 4;
get_orientation(points+pp,points+pp+4*enn,points+pp+4*2*enn, f_prm_0, &yaw, &pch, &rll);
if (!(count%print_int)&&!estimate_f) {
printf("%.10g\t%.10g\t%.10g\t%.10g\t%.10g\t%.10g\t%.10g\n",points[pp+0],points[pp+1],points[pp+2],points[pp+3],yaw,pch,rll);
}
if (pp >= 4*enn)
status=MIDDLE;
break;
case MIDDLE: /* middle points (at least one)*/
for (i=0; i<3*enn*4; i++){
VMOVEN(points+(4*i), points+(4*(i+1)), 4);
}
num_read=scanf("%lf %lf %lf %lf", points+(4*(3*enn)),points+(4*(3*enn)+1),points+(4*(3*enn)+2),points+(4*(3*enn)+3));
if (num_read < 4) {
pp = 0;
status = WANE;
}
get_orientation(points,points+(4*enn),points+4*(2*enn), f_prm_1, &yaw, &pch, &rll);
if (!(count%print_int)&&!estimate_f) {
printf("%.10g\t%.10g\t%.10g\t%.10g\t%.10g\t%.10g\t%.10g\n",points[4*(enn)+0],points[4*(enn)+1],points[4*(enn)+2],points[4*(enn)+3],yaw,pch,rll);
}
break;
case WANE: /* last n - 1 middle points */
pp += 4;
if (pp >= 4*enn){
status = END;
count--;
pp = 0;
break;
}
get_orientation(points+pp,points+pp+4*enn,points+pp+4*2*enn, f_prm_1, &yaw, &pch, &rll);
if (!(count%print_int)&&!estimate_f) {
printf("%.10g\t%.10g\t%.10g\t%.10g\t%.10g\t%.10g\t%.10g\n",points[4*(enn)+0+pp],points[4*(enn)+1+pp],points[4*(enn)+2+pp],points[4*(enn)+3+pp],yaw,pch,rll);
}
break;
case END: /* last n points */
get_orientation(points+pp,points+pp+4*enn,points+pp+4*2*enn, f_prm_2, &yaw, &pch, &rll);
if (!(count%print_int)&&!estimate_f) {
printf("%.10g\t%.10g\t%.10g\t%.10g\t%.10g\t%.10g\t%.10g\n",points[8*enn+pp+0],points[8*enn+pp+1],points[8*enn+pp+2],points[8*enn+pp+3],yaw,pch,rll);
}
pp += 4;
if (pp >= 4*enn)
status = STOP;
break;
}
count++;
}
/* Return the factor needed to achieve the requested max_bank */
if (estimate_f){
if (max_cross < VDIVIDE_TOL) {
printf("%.10g\n",0.0);
} else {
printf("%.10g\n", 1000.0 * max_bank/max_cross);
}
}
return( 0 );
}
void
get_orientation(p0,p1,p2,function, p_yaw, p_pch, p_rll)
fastf_t p0[4],p1[4],p2[4], *p_yaw, *p_pch, *p_rll;
fastf_t (*function)();
{
int i;
fastf_t step,vel[3],accel[3];
fastf_t f_double_prm(),xyz2yaw(),xyz2pch(),bank();
static fastf_t last_yaw;
static int not_first_time, upside_down;
step = p2[0] - p1[0];
for (i=1;i<4;i++) {
vel[i-1] = (*function)(p0[i],p1[i],p2[i],step);
accel[i-1] = f_double_prm(p0[i],p1[i],p2[i],step);
}
*p_yaw = xyz2yaw(vel);
*p_pch = xyz2pch(vel);
*p_rll = bank(accel,vel);
if (fabs(*p_pch)==90.0) /* don't change yaw if velocity vertical */
*p_yaw = last_yaw;
/* avoid sudden yaw changes in vertical loops */
if (not_first_time&&loop){
if ((fabs(last_yaw - *p_yaw)<181.0)&&(fabs(last_yaw - *p_yaw)>179.0))
upside_down = (upside_down) ? 0 : 1;
if (upside_down)
(*p_rll) += 180;
}
last_yaw = *p_yaw;
not_first_time = 1;
}
/* determine the yaw of the given direction vector */
fastf_t xyz2yaw(d)
fastf_t d[3];
{
fastf_t yaw;
yaw = RTOD*atan2(d[1],d[0]);
if (yaw < 0.0) yaw += 360.0;
return yaw;
}
/* determine the pitch of the given direction vector */
fastf_t xyz2pch(d)
fastf_t d[3];
{
fastf_t x;
x = sqrt(d[0]*d[0] + d[1]*d[1]);
return (RTOD*atan2(d[2],x));
}
/* given the 3-d velocity and acceleration of an imaginary aircraft,
find the amount of bank the aircraft would need to undergo.
Algorithm: the bank angle is proportional to the cross product
of the horizontal velocity and horizontal acceleration, up to a
maximum bank of 90 degrees in either direction. */
fastf_t bank(acc,vel)
fastf_t acc[3],vel[3];
{
fastf_t cross;
cross = vel[1]*acc[0] - vel[0]*acc[1];
if (estimate_f) {
max_cross = ( fabs(cross) > max_cross) ? fabs(cross) : max_cross;
}
cross *= magic_factor;
if (cross > 90) cross = 90;
if (cross < -90) cross = -90;
return cross;
}
/* given f(t), f(t+h), f(t+2h), and h, calculate f'(t) */
fastf_t f_prm_0(x0,x1,x2,h)
fastf_t x0,x1,x2,h;
{
return -(3.0*x0 - 4.0*x1 + x2)/(2*h);
}
/* given f(t), f(t+h), f(t+2h), and h, calculate f'(t+h) */
fastf_t f_prm_1(x0,x1,x2,h)
fastf_t x0,x1,x2,h;
{
return (x2 - x0)/(2*h);
}
/* given f(t), f(t+h), f(t+2h), and h, calculate f'(t+2h) */
fastf_t f_prm_2(x0,x1,x2,h)
fastf_t x0,x1,x2,h;
{
return (x0 - 4.0*x1 + 3.0*x2)/(2*h);
}
/* given f(t), f(t+h), f(t+2*h), and h, calculate f'' */
fastf_t f_double_prm(x0,x1,x2,h)
fastf_t x0,x1,x2,h;
{
return (x0 - 2.0*x1 + x2)/(h*h);
}
/* code to read command line arguments*/
#define OPT_STR "b:f:p:s:r"
int get_args(argc,argv)
int argc;
char **argv;
{
int c;
estimate_f = 0;
while ( (c=bu_getopt(argc,argv,OPT_STR)) != EOF) {
switch(c){
case 'b':
sscanf(bu_optarg,"%lf",&max_bank);
estimate_f = 1;
break;
case 'f':
sscanf(bu_optarg,"%lf",&magic_factor);
magic_factor *= 0.001; /* to put factors in a more reasonable range */
break;
case 'p':
sscanf(bu_optarg,"%d",&print_int);
break;
case 'r':
loop = 0;
break;
case 's':
sscanf(bu_optarg, "%lf", &desired_step);
break;
default:
fprintf(stderr,"Unknown option: -%c\n",c);
return(0);
}
}
return(1);
}
+241
View File
@@ -0,0 +1,241 @@
/* A N I M _ F L Y . C
*
* Simulate flying motion, for an airplane or virtual camera.
*
* This filter operates on animation tables. Given the desired position
* of the airplane in each frame, anim_fly produces a table including the
* plane's position and orientation. A "magic factor" should be supplied
* to control the severity of banking. Looping behavior can be toggled
* with another option.
*
* Author -
* Carl J. Nuzman
*
* Source -
* The U. S. Army Research Laboratory
* Aberdeen Proving Ground, Maryland 21005-5068 USA
*
* Distribution Notice -
* Re-distribution of this software is restricted, as described in
* your "Statement of Terms and Conditions for the Release of
* The BRL-CAD Pacakge" agreement.
*
* Copyright Notice -
* This software is Copyright (C) 1993-2004 by the United States Army
* in all countries except the USA. All rights reserved.
*/
#include <math.h>
#include <stdio.h>
#include "machine.h"
#include "vmath.h"
#include "anim.h"
#ifndef M_PI
#define M_PI 3.14159265358979323846
#endif
extern int bu_optind;
extern char *bu_optarg;
int loop = 1;
int print_int = 1;
fastf_t magic_factor = 1.0;
#define PREP -1
#define START 0
#define MIDDLE 1
#define END 2
#define STOP 3
main(argc,argv)
int argc;
char **argv;
{
int count, status, num_read;
fastf_t point0[4],point1[4],point2[4],point3[4], yaw, pch, rll;
fastf_t f_prm_0(), f_prm_1(), f_prm_2();
VSETALL(point0,0.0);
VSETALL(point1,0.0);
VSETALL(point2,0.0);
VSETALL(point3,0.0);
yaw = pch = rll = 0.0;
if (!get_args(argc,argv))
fprintf(stderr,"Anim_fly: Get_args error");
count = -2;
status = PREP;
num_read = 4;
while (status != STOP) {
/* check for end of file status */
if (num_read < 4) status = END;
/*wait twice to prime the pump before starting calculations*/
if (!(count++)) status = START;
/* read one line of the table into point3, storing
previous values in point0, point1, and point2. */
if (status != END) {
VMOVEN(point0,point1,4);
VMOVEN(point1,point2,4);
VMOVEN(point2,point3,4);
num_read = scanf("%lf %lf %lf %lf", point3, point3+1, point3+2, point3+3);
}
if (status==START) { /* do calculations for the first point*/
get_orientation(point1,point2,point3, f_prm_0, &yaw, &pch, &rll);
if (!(count%print_int)) {
printf("%f %f %f %f %f %f %f\n",point1[0],point1[1],point1[2],point1[3],yaw,pch,rll);
}
status = MIDDLE;
}
else if (status==MIDDLE) {/*do calculations for all middle points*/
get_orientation(point0,point1,point2, f_prm_1, &yaw, &pch, &rll);
if (!(count%print_int)) {
printf("%f %f %f %f %f %f %f\n",point1[0],point1[1],point1[2],point1[3],yaw,pch,rll);
}
}
else if (status==END) { /*do calculations for the last point*/
get_orientation(point0,point1,point2, f_prm_2, &yaw, &pch, &rll);
if (!(count%print_int)) {
printf("%f %f %f %f %f %f %f\n",point2[0],point2[1],point2[2],point2[3],yaw,pch,rll);
}
status = STOP;
}
}
}
get_orientation(p0,p1,p2,function, p_yaw, p_pch, p_rll)
fastf_t p0[4],p1[4],p2[4], *p_yaw, *p_pch, *p_rll;
fastf_t (*function)();
{
int i;
fastf_t step,vel[3],accel[3];
fastf_t f_double_prm(),xyz2yaw(),xyz2pch(),bank();
static fastf_t last_yaw, last_pch, last_rll;
static int not_first_time, upside_down;
step = p2[0] - p1[0];
for (i=1;i<4;i++) {
vel[i-1] = (*function)(p0[i],p1[i],p2[i],step);
accel[i-1] = f_double_prm(p0[i],p1[i],p2[i],step);
}
*p_yaw = xyz2yaw(vel);
*p_pch = xyz2pch(vel);
*p_rll = bank(accel,vel);
if (fabs(*p_pch)==90.0) /* don't change yaw if velocity vertical */
*p_yaw = last_yaw;
/* avoid sudden yaw changes in vertical loops */
if (not_first_time&&loop){
if ((fabs(last_yaw - *p_yaw)<181.0)&&(fabs(last_yaw - *p_yaw)>179.0))
upside_down = (upside_down) ? 0 : 1;
if (upside_down)
(*p_rll) += 180;
}
last_yaw = *p_yaw;
last_pch = *p_pch;
last_rll = *p_rll;
not_first_time = 1;
}
/* determine the yaw of the given direction vector */
fastf_t xyz2yaw(d)
fastf_t d[3];
{
fastf_t yaw;
yaw = RTOD*atan2(d[1],d[0]);
if (yaw < 0.0) yaw += 360.0;
return yaw;
}
/* determine the pitch of the given direction vector */
fastf_t xyz2pch(d)
fastf_t d[3];
{
fastf_t x;
x = sqrt(d[0]*d[0] + d[1]*d[1]);
return (RTOD*atan2(d[2],x));
}
/* given the 3-d velocity and acceleration of an imaginary aircraft,
find the amount of bank the aircraft would need to undergo.
Algorithm: the bank angle is proportional to the cross product
of the horizontal velocity and horizontal acceleration, up to a
maximum bank of 90 degrees in either direction. */
fastf_t bank(acc,vel)
fastf_t acc[3],vel[3];
{
fastf_t cross;
cross = vel[1]*acc[0] - vel[0]*acc[1];
cross *= magic_factor;
if (cross > 90) cross = 90;
if (cross < -90) cross = -90;
return cross;
}
/* given f(t), f(t+h), f(t+2h), and h, calculate f'(t) */
fastf_t f_prm_0(x0,x1,x2,h)
fastf_t x0,x1,x2,h;
{
return -(3.0*x0 - 4.0*x1 + x2)/(2*h);
}
/* given f(t), f(t+h), f(t+2h), and h, calculate f'(t+h) */
fastf_t f_prm_1(x0,x1,x2,h)
fastf_t x0,x1,x2,h;
{
return (x2 - x0)/(2*h);
}
/* given f(t), f(t+h), f(t+2h), and h, calculate f'(t+2h) */
fastf_t f_prm_2(x0,x1,x2,h)
fastf_t x0,x1,x2,h;
{
return (x0 - 4.0*x1 + 3.0*x2)/(2*h);
}
/* given f(t), f(t+h), f(t+2*h), and h, calculate f'' */
fastf_t f_double_prm(x0,x1,x2,h)
fastf_t x0,x1,x2,h;
{
return (x0 - 2.0*x1 + x2)/(h*h);
}
/* code to read command line arguments*/
#define OPT_STR "f:p:r"
int get_args(argc,argv)
int argc;
char **argv;
{
int c;
while ( (c=bu_getopt(argc,argv,OPT_STR)) != EOF) {
switch(c){
case 'f':
sscanf(bu_optarg,"%lf",&magic_factor);
magic_factor *= 0.001; /* to put factors in a more reasonable range */
break;
case 'p':
sscanf(bu_optarg,"%d",&print_int);
break;
case 'r':
loop = 0;
break;
default:
fprintf(stderr,"Unknown option: -%c\n",c);
return(0);
}
}
return(1);
}
+293
View File
@@ -0,0 +1,293 @@
.TH ANIM_HARDTRACK 1 BRL/CAD
.SH NAME
anim_hardtrack - make an animation script for the links and/or wheels of a
tracked vehicle with rigid axles.
.SH SYNOPSIS
.B
anim_hardtrack [-l num_links linkname] [-w wheelname] [options] wheelfile < in.table > out.script
.SH DESCRIPTION
.I Anim_hardtrack
is designed to produce an animation script for the
animation of a track and/or the wheels defining a track, where the wheels
are rigidly fixed in place with respect to the vehicle. The main
difference between
.I anim_hardtrack
and
.I anim_track
is that
.I anim_track
handles vehicles with dynamic axles. Both are designed to be use in
conjunction with
.I anim_script,
to achieve the final result.
.PP
.B in.table
is the file that will be used to animate the
vehicle itself. By default, it is assumed that it contains a time column,
three columns of translation information, and three columns specifying the
vehicle's yaw, pitch, and roll. If it is desired that the vehicle be steered
automatically, then the table should contain only time and position, and the
.B -s
option should be used.
.PP
The track's
geometry is defined by
.BR wheelfile ,
a table which contains one row for each wheel defining the track. The
first three columns of the table specify the x, y, and z coordinates of
the wheel centers. The fourth column specifies the radius of each wheel.
.PP
The order in which the wheels are listed should be the order in which a
link of the track would move around the wheels when the vehicle is moving
forward. (clockwise, when looking from the right of the vehicle).
The wheel centers should all lie in a plane perpendicular to the vehicle's
left-right axis. If this is not the case,
.I anim_hardtrack
uses the first wheel as the standard and projects all the other wheels into
the same plane as the first wheel. By default, it is assumed that the
vehicle's left-right axis is the y-axis. If the modeled vehicle has some
other orientation, this must be specified with the
.B -b
option.
.PP
By default, it is
assumed that
all of the link objects are modeled at the model origin,
with the wheel-contacting surface centered on the origin and the
ground-contacting surface facing up. The sides of each link which
connect to other links should face the positive and negative x-axes.
.I Anim_hardtrack
prints the appropriate
commands to move the links from
the origin to the correct place around the wheels.
.PP
If the links are modeled in place around the wheels to begin with, the
the
.B -p
and
.B -i
options are needed.
.SH OPTIONS:
.PP
One or both of the first two options should always be specified.
.TP
.B \-l num linkname
Print animation scripts to animate the links of the track. Animation
commands will be printed for
.I num
different links
named
.IR linkname .0, linkname .1,
up through
.IR linkname .( num -1).
A typical example of a linkname might
be "tank/righttrack/links/link". The full pathname must be specified,
because anim_hardtrack's method is to roll the links around within
the vehicle's tree structure so that when the whole vehicle "tank" is
animated, the complete combination of rolling around and translating is
achieved.
.TP
.B \-w wheelname
Print animation
scripts to rotate each wheel. The wheels are named wheelname.0, wheelname.1,
and so on, where wheelname.0 is the first wheel listed in
.BR wheelfile .
As with the links, the full pathname for the wheels should be specified.
.TP
.B \-b # # #
Specify the yaw, pitch, and roll of the vehicle's axes
with respect to the world axes. By default, the vehicle is assumed to
have a yaw, pitch, and roll of 0.
.TP
.B \-d # # #
Specify (in world coordinates) the centroid of the vehicle
of which the track is a part. By default, the vehicle is assumed
centered at the origin.
.PP
When calling
.I anim_script
to handle the animation of the vehicle
itself, the parameters following the
.B -b
and
.B -d
options should be identical
to those used for
.IR anim_hardtrack .
.TP
.B \-r #
Specify the common radius of all wheels. In this case the fourth column
should be omitted from the
.BR wheelfile .
.TP
.B \-s
Automatic steering. In this case,
.B in.table
specifies only the time and position
of the vehicle. The orientation is calculated to always face the vehicle
in the direction of motion.
This should be used when the
.B \-s
option is used by
.I anim_script
to animate the vehicle.
.PP
.TP
.B \-f#
Specify the integer with which to begin numbering frames.
Default is zero.
.TP
.B \-p
Animate placed links, rather than links stored at the origin.
In order for placed links to be animated, they must be equally spaced
around the wheels defining the track. The track must be formed of arcs
around the wheels and straight lines between the wheels, and the links
must be numbered clockwise as seen from the right.
By default, it is assumed that the
center of the first link, linkname.0, is at the beginning of the
straight track segment between wheel.(n-1) and wheel.0 . If this is
not the case, the position of the first link must be identified with the
.B \-i#
option.
.TP
.B \-i#
Specify the initial offset of the first link. If this option is
not used, the initial position of linkname.0 is assumed to be the
beginning of the straight track segment between wheel.(n-1) and wheel.0.
If it is used, the argument specifies the distance clockwise around the
track from the default position to the actual desired offset. If the
links are modeled at the origin, the user can choose any offset. This
can be useful for lining up the links with gears of a drive wheel, for
example.
If the
.B -p
option is being used to animated pre-placed links, then it is essential
that the actual offset of the first pre-placed link be specified.
.SS Output:
.PP
The output is a script containing as many frames as there
are positions in
.BR in.table .
If there are
.I n
links and
.I k
wheels, each
frame contains up to
.IR n + k
anim commands, either:
.nf
anim linkname.i matrix lmul
[... matrix ...] ;
or
anim wheelname.j matrix lmul
[... matrix ...] ;
for 0<=i<n and 0<=j<k.
.fi
.SH EXAMPLES
Suppose you want to make an animation of a tank rolling across
flat ground. A list of desired positions is created, perhaps by
interpolating between a few key positions; this information is placed
in a four column animation table, in.table. The model of the tank is stored in
model.g as a combination named "tank". Its centroid is at the
point (0,0,1000) and it faces the y-axis. An animation script for the
tank itself is created as follows:
.PP
anim_script -s -d 0 0 1000 -b 90 0 0 /tank < in.table > tank.script
.PP
Suppose that there are two
roadwheels and a drivewheel (tank/rwheel/wheel.i, 0<=i<3) which define
the shape of the right track.
A file called
.B rwheelfile
is created:
.nf
1500 -2000 30 30
1500 0 1000 35
1500 2000 30 30
.fi
This
.B rwheelfile
lists the position and
radius of each of the three wheels.
.PP
There are eighty links which make up the right track
(tank/rtrack/link.i, 0<=i<80).
The links of the right track are all modeled
at the origin with the outer, ground-contacting surface
facing up and the inner, wheel-contacting surface centered at the
origin.
.PP
The appropriate call to
.I anim_hardtrack
is now:
.sp
anim_hardtrack -d 0 0 1000 -b 90 0 0 -w tank/rwheel -l 80 tank/rtrack/link
rwheelfile < in.table > rtrack.script
.sp
Suppose that the left track is similar to the right track,
except that all the wheels are of radius 30 units, and the links, rather
than being stored at the origin, are actually placed in position around
the left wheels to begin with. The
.B lwheelfile
would be:
.nf
-1500 -2000 30
-1500 0 1000
-1500 2000 30
.fi
and the call would be:
.sp
anim_hardtrack -p -r 30 -d 0 0 1000 -b 90 0 0 -w tank/lwheel
-l 80 tank/ltrack/link lwheelfile <in.table > ltrack.script
.sp
Here, it is assumed that tank/ltrack/link.0 is initially at the
beginning of the straight track segment between lwheel.2 and lwheel.0,
that is, at the point (2000,1500,-1000) in the vehicle's coordinates.
If, instead, the first link is initially centered halfway between the
two roadwheels, this must be specified with the
.B -i#
option. If the link's
actual position is 2000 units farther around the track than expected:
.sp
anim_hardtrack -i 2000 -p -r 30 -d 0 0 1000 -b 90 0 0 -w tank/lwheel
-l 80 tank/ltrack/link lwheelfile <in.table > ltrack.script
.sp
One final step may remain. The above procedure produces a script with rigid
naming conventions, in order to make input simple. This may mean that
the names in the script do not match the names in model.g. An editor
should then be used at the end to replace all instances of the
conventional name with the real name; for example, in this case it may
be necessary to replace "rwheel.1" with "r_drivewheel".
.PP
.BR Tank.script ,
.BR rtrack.script ,
and
.B ltrack.script
can be combined
with
.I anim_sort
to make the complete script.
.PP
.SH BUGS
Tracks must have at least two wheels, and they must be listed in clockwise
order, or the results are unpredictable.
.SH SEE ALSO
anim_script(1), anim_track(1)
.SH AUTHOR
Carl J. Nuzman
.SH COPYRIGHT
This software is Copyright (C) 1993-2004 by the United States Army
in all countries except the USA. All rights reserved.
.SH "BUG REPORTS"
Reports of bugs or problems should be submitted via electronic
mail to <CAD@ARL.ARMY.MIL>.
+517
View File
@@ -0,0 +1,517 @@
/* A N I M _ H A R D T R A C K . C
*
* Animate the links and wheels of a tracked vehicle. It is assumed
* that the wheels do not translate with respect to the vehicle.
*
* Author -
* Carl J. Nuzman
*
* Source -
* The U. S. Army Research Laboratory
* Aberdeen Proving Ground, Maryland 21005-5068 USA
*
* Distribution Notice -
* Re-distribution of this software is restricted, as described in
* your "Statement of Terms and Conditions for the Release of
* The BRL-CAD Pacakge" agreement.
*
* Copyright Notice -
* This software is Copyright (C) 1993-2004 by the United States Army
* in all countries except the USA. All rights reserved.
*/
#include "conf.h"
#ifdef USE_STRING_H
#include <string.h>
#else
#include <strings.h>
#endif
#include <math.h>
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include "machine.h"
#include "vmath.h"
#include "bu.h"
#include "bn.h"
#include "anim.h"
#ifndef M_PI
#define M_PI 3.14159265358979323846
#endif
#ifndef M_PI_2
#define M_PI_2 (M_PI*0.5)
#endif
#define NW num_wheels
#define NEXT(i) (i+1)%NW
#define PREV(i) (i+NW-1)%NW
#define TRACK_ANIM 0
#define TRACK_ARCED 1
typedef double *pdouble;
struct wheel {
vect_t pos; /* displacement of wheel from vehicle origin */
fastf_t rad; /* radius of wheel */
fastf_t ang0; /* angle where track meets wheel; 0 < a < 2pi */
fastf_t ang1; /* angle where track leaves wheel; 0 < a < 2pi */
fastf_t arc; /* arclength of contact between wheel and track */
};
struct track {
vect_t pos0; /* beginning point of track section */
vect_t pos1; /* end point of track section */
vect_t dir; /* unit vector: direction of track section */
fastf_t len; /* length of track section */
};
struct slope {
vect_t dir; /* vector from previous to current axle */
fastf_t len; /* length of vector described above */
};
struct all {
struct wheel w; /* parameters describing the track around a wheel */
struct track t; /* track between this wheel and the previous wheel */
struct slope s; /* vector between this axle and the previous axle */
};
struct rlink {
vect_t pos; /* reverse of initial position */
fastf_t ang; /* initial angle */
};
/* external variables */
extern int bu_optind;
extern char *bu_optarg;
/* variables describing track geometry - used by main, trackprep, get_link */
struct all *x;
struct rlink *r; /* reverse of initial locations of links */
int num_links, num_wheels;
fastf_t track_y, tracklen;
/* variables set by get_args */
int wheel_nindex; /* argv[wheel_nindex] = wheelname*/
int link_nindex; /* argv[link_nindex] = linkname*/
int print_wheel; /* flag: do wheel animation */
int print_link; /* flag: do link animation */
int print_mode; /* anim for rt or arced for mged */
int arced_frame; /* which frame to arced */
int links_placed; /* flag: links are initially on the track */
int axes, cent; /* flags: alternate axes, centroid specified */
int steer; /* flag: vehicle automatically steered */
int first_frame; /* integer with which to begin numbering frames */
fastf_t radius; /* common radius of all wheels */
fastf_t init_dist; /* initial distance of first link along track */
vect_t centroid, rcentroid; /* alternate centroid and its reverse */
mat_t m_axes, m_rev_axes; /* matrices to and from alternate axes */
char link_cmd[10]; /* default is "rarc" */
char wheel_cmd[10]; /* default is "lmul" */
int get_circumf; /* flag: just return circumference of track */
int get_link();
int
main(argc,argv)
int argc;
char **argv;
{
void anim_dir2mat(), anim_y_p_r2mat(), anim_add_trans(),anim_mat_print();
int get_args(), track_prep(), val, frame, go, i, count;
fastf_t y_rot, distance, yaw, pitch, roll;
vect_t p1, p2, p3, dir, dir2, wheel_now, wheel_prev;
vect_t zero, position, vdelta, temp, to_track, to_front;
mat_t mat_v, wmat, mat_x;
FILE *stream;
int last_frame;
VSETALL(zero,0.0);
VSETALL(to_track,0.0);
VSETALL(centroid,0.0);
VSETALL(rcentroid,0.0);
init_dist = y_rot = radius= 0.0;
first_frame = num_wheels = steer = axes = cent = links_placed=0;
num_wheels = num_links = last_frame = 0;
MAT_IDN(mat_v);
MAT_IDN(mat_x);
MAT_IDN(wmat);
MAT_IDN(m_axes);
MAT_IDN(m_rev_axes);
if (!get_args(argc,argv)){
fprintf(stderr,"anim_hardtrack: argument error.");
return(-1);
}
if (axes || cent ){ /* vehicle has own reference frame */
anim_add_trans(m_axes,centroid,zero);
anim_add_trans(m_rev_axes,zero,rcentroid);
}
/* get track information from specified file */
if (!(stream = fopen(*(argv+bu_optind),"r"))){
fprintf(stderr,"Anim_hardtrack: Could not open file %s.\n",*(argv+bu_optind));
return(0);
}
num_wheels = -1;
if (radius) {
while (!feof(stream)) {
fscanf(stream,"%*f %*f %*f");
num_wheels++;
}
} else {
while (!feof(stream)) {
fscanf(stream,"%*f %*f %*f %*f");
num_wheels++;
}
}
rewind(stream);
/*allocate memory for track information*/
x = (struct all *) calloc(num_wheels,sizeof(struct all));
/*read rest of track info */
for (i=0;i<NW;i++){
fscanf(stream,"%lf %lf %lf", temp, temp+1, temp+2);
if (radius)
x[i].w.rad = radius;
else
fscanf(stream,"%lf",& x[i].w.rad);
MAT4X3PNT(x[i].w.pos,m_rev_axes,temp);
if (i==0)
track_y = x[0].w.pos[1];
else
x[i].w.pos[1] = track_y;
}
(void) fclose(stream);
(void) track_prep();
if (get_circumf) {
printf("%.10g\n",tracklen);
return(0);
}
/* initialize to_track */
VSET(to_track, 0.0, track_y, 0.0);
VSET(to_front,1.0,0.0,0.0);
if ((!print_link)&&(!print_wheel)) {
fprintf(stderr,"anim_hardtrack: no ouput requested. Use -l or -w.\n");
exit(0);
}
/* main loop */
distance = 0.0;
if(!steer)
frame = first_frame;
else
frame = first_frame-1;
for (val = 3; val > 2; frame++) {
go = 1;
/*p2 is current position. p3 is next;p1 is previous*/
VMOVE(p1,p2);
VMOVE(p2,p3);
scanf("%*f");/*time stamp*/
val = scanf("%lf %lf %lf", p3, p3+1, p3 + 2);
if(!steer){
scanf("%lf %lf %lf",&yaw,&pitch,&roll);
anim_dy_p_r2mat(mat_v,yaw,pitch,roll);
anim_add_trans(mat_v,p3,rcentroid);
}
else { /* analyze positions for steering */
/*get useful direction unit vectors*/
if (frame == first_frame){ /* first frame*/
VSUBUNIT(dir,p3,p2);
VMOVE(dir2,dir);
}
else if (val < 3){ /*last frame*/
VSUBUNIT(dir,p2,p1);
VMOVE(dir2,dir);
}
else if (frame > first_frame){ /*normal*/
VSUBUNIT(dir,p3,p1);
VSUBUNIT(dir2,p2,p1);/*needed for vertical case*/
}
else go = 0;/*first time through loop;no p2*/
/*create matrix which would move vehicle*/
anim_dir2mat(mat_v,dir,dir2);
anim_add_trans(mat_v,p2,rcentroid);
}
/*determine distance traveled*/
VMOVE(wheel_prev,wheel_now);
MAT4X3PNT(wheel_now,mat_v,to_track);
if (frame > first_frame){ /* increment distance by distance moved */
VSUB2(vdelta,wheel_now,wheel_prev);
MAT3X3VEC(temp,mat_v,to_front);/*new front of vehicle*/
distance += VDOT(temp,vdelta);/*portion of vdelta in line with track*/
}
if (go){
if (print_mode==TRACK_ANIM) {
printf("start %d;\nclean;\n", frame);
} else if (print_mode==TRACK_ARCED) {
if (frame != arced_frame) continue;
last_frame = 1;
}
if (print_link) {
for (count=0;count<num_links;count++){
(void) get_link(position,&y_rot,distance+tracklen*count/num_links+init_dist);
anim_y_p_r2mat(wmat,0.0,y_rot+r[count].ang,0.0);
anim_add_trans(wmat,position,r[count].pos);
if ((axes || cent) && links_placed){ /* link moved from vehicle coords */
bn_mat_mul(mat_x,wmat,m_rev_axes);
bn_mat_mul(wmat,m_axes,mat_x);
}
else if (axes || cent){ /* link moved to vehicle coords */
MAT_MOVE(mat_x,wmat);
bn_mat_mul(wmat,m_axes,mat_x);
}
if (print_mode==TRACK_ANIM) {
printf("anim %s.%d matrix %s\n", *(argv+link_nindex),count,link_cmd);
anim_mat_printf(stdout,wmat,"%.10g ","\n",";\n");
} else if (print_mode==TRACK_ARCED) {
printf("arced %s.%d matrix %s ", *(argv+link_nindex),count,link_cmd);
anim_mat_printf(stdout,wmat,"%.10g ","","\n");
}
}
}
if (print_wheel){
for (count = 0;count<num_wheels;count++){
anim_y_p_r2mat(wmat,0.0,-distance/x[count].w.rad,0.0);
VREVERSE(temp,x[count].w.pos);
anim_add_trans(wmat,x[count].w.pos,temp);
if (axes || cent){
bn_mat_mul(mat_x,wmat,m_rev_axes);
bn_mat_mul(wmat,m_axes,mat_x);
}
if (print_mode==TRACK_ANIM) {
printf("anim %s.%d matrix %s\n",*(argv+wheel_nindex),count,wheel_cmd);
anim_mat_printf(stdout,wmat,"%.10g ","\n",";\n");
} else if (print_mode==TRACK_ARCED) {
printf("arced %s.%d matrix %s ",*(argv+wheel_nindex),count,wheel_cmd);
anim_mat_printf(stdout,wmat,"%.10g ","","\n");
}
}
}
if (print_mode==TRACK_ANIM)
printf("end;\n");
}
if (last_frame) break;
}
return( 0 );
}
int track_prep()/*run once at the beginning to establish important track info*/
{
int i;
fastf_t phi, costheta, link_angle, arc_angle;
vect_t difference, link_cent;
/* first loop - get inter axle slopes and start/end angles */
for (i=0;i<NW;i++){
/*calculate current slope vector*/
VSUB2(x[i].s.dir,x[i].w.pos,x[PREV(i)].w.pos);
x[i].s.len = MAGNITUDE(x[i].s.dir);
/*calculate end angle of previous wheel - atan2(y,x)*/
phi = atan2(x[i].s.dir[2],x[i].s.dir[0]);/*absolute angle of slope*/
costheta = (x[PREV(i)].w.rad - x[i].w.rad)/x[i].s.len;/*cosine of special angle*/
x[PREV(i)].w.ang1 = phi + acos(costheta);
while (x[PREV(i)].w.ang1 < 0.0)
x[PREV(i)].w.ang1 += 2.0*M_PI;
x[i].w.ang0 = x[PREV(i)].w.ang1;
}
/* second loop - handle concavities */
for (i=0;i<NW;i++){
arc_angle = x[i].w.ang0 - x[i].w.ang1;
while (arc_angle < 0.0)
arc_angle += 2.0*M_PI;
if (arc_angle > M_PI) { /* concave */
x[i].w.ang0 = 0.5*(x[i].w.ang0 + x[i].w.ang1);
x[i].w.ang1 = x[i].w.ang0;
x[i].w.arc = 0.0;
}
else { /* convex - angles are already correct */
x[i].w.arc = arc_angle;
}
}
/* third loop - calculate geometry of track segments */
tracklen = 0.0;
for (i=0;i<NW;i++){
/*calculate endpoints of track segment*/
x[i].t.pos1[0] = x[i].w.pos[0] + x[i].w.rad*cos(x[i].w.ang0);
x[i].t.pos1[1] = x[i].w.pos[1];
x[i].t.pos1[2] = x[i].w.pos[2] + x[i].w.rad*sin(x[i].w.ang0);
x[i].t.pos0[0] = x[PREV(i)].w.pos[0] + x[PREV(i)].w.rad*cos(x[PREV(i)].w.ang1);
x[i].t.pos0[1] = x[PREV(i)].w.pos[1];
x[i].t.pos0[2] = x[PREV(i)].w.pos[2] + x[PREV(i)].w.rad*sin(x[PREV(i)].w.ang1);
/*calculate length and direction*/
VSUB2(difference,x[i].t.pos1,x[i].t.pos0);
x[i].t.len = MAGNITUDE(difference);
VSCALE((x[i].t.dir),difference,(1.0/x[i].t.len));
/*calculate arclength and total track length*/
tracklen += x[i].t.len;
tracklen += x[i].w.arc*x[i].w.rad;
}
/* for a track with links already placed, get initial positions*/
r = (struct rlink *) calloc(num_links, sizeof(struct rlink));
if (links_placed)
for (i=0;i<num_links;i++){
get_link(link_cent,&link_angle,init_dist + tracklen*i/num_links);
VREVERSE(r[i].pos,link_cent);
r[i].ang = -link_angle;
}
return(0);
}
int get_link(pos,angle_p,dist)
fastf_t *angle_p, dist;
vect_t pos;
{
int i;
vect_t temp;
while (dist >= tracklen) /*periodicize*/
dist -= tracklen;
while (dist < 0.0)
dist += tracklen;
for (i=0;i<NW;i++){
if ( (dist -= x[i].t.len) < 0 ){
VSCALE(temp,(x[i].t.dir),dist);
VADD2(pos,x[i].t.pos1,temp);
*angle_p = atan2(x[i].t.dir[2],x[i].t.dir[0]);
return(2*i);
}
if ((dist -= x[i].w.rad*x[i].w.arc) < 0){
*angle_p = dist/x[i].w.rad;
*angle_p = x[i].w.ang1 - *angle_p;/*from x-axis to link*/
pos[0] = x[i].w.pos[0] + x[i].w.rad*cos(*angle_p);
pos[1] = x[i].w.pos[1];
pos[2] = x[i].w.pos[2] + x[i].w.rad*sin(*angle_p);
*angle_p -= M_PI_2; /*angle of clockwise tangent to circle*/
return(2*i+1);
}
}
return -1;
}
#define OPT_STR "b:d:f:i:l:pr:w:sg:m:c"
int get_args(argc,argv)
int argc;
char **argv;
{
fastf_t yaw, pch, rll;
void anim_dx_y_z2mat(), anim_dz_y_x2mat();
int c, i;
axes = cent = links_placed = print_wheel = print_link = 0;
get_circumf = 0;
print_mode = TRACK_ANIM;
strcpy(link_cmd, "rarc");
strcpy(wheel_cmd, "lmul");
while ( (c=bu_getopt(argc,argv,OPT_STR)) != EOF) {
i=0;
switch(c){
case 'b':
bu_optind -= 1;
sscanf(argv[bu_optind+(i++)],"%lf", &yaw );
sscanf(argv[bu_optind+(i++)],"%lf", &pch );
sscanf(argv[bu_optind+(i++)],"%lf", &rll );
bu_optind += 3;
anim_dx_y_z2mat(m_axes, rll, -pch, yaw);
anim_dz_y_x2mat(m_rev_axes, -rll, pch, -yaw);
axes = 1;
break;
case 'd':
bu_optind -= 1;
sscanf(argv[bu_optind+(i++)],"%lf",centroid);
sscanf(argv[bu_optind+(i++)],"%lf",centroid+1);
sscanf(argv[bu_optind+(i++)],"%lf",centroid+2);
bu_optind += 3;
VREVERSE(rcentroid,centroid);
cent = 1;
break;
case 'f':
sscanf(bu_optarg,"%d",&first_frame);
break;
case 'i':
sscanf(bu_optarg,"%lf",&init_dist);
break;
case 'p':
links_placed = 1;
break;
case 'r':
sscanf(bu_optarg,"%lf",&radius);
break;
case 'w':
wheel_nindex = bu_optind - 1;
/*sscanf(bu_optarg,"%s",wheel_name);*/
print_wheel = 1;
break;
case 'l':
sscanf(bu_optarg,"%d", &num_links);
link_nindex = bu_optind;
bu_optind += 1;
print_link = 1;
break;
case 's':
steer = 1;
break;
case 'g':
sscanf(bu_optarg,"%d",&arced_frame);
print_mode = TRACK_ARCED;
break;
case 'm':
switch (*bu_optarg) {
case 'l':
strncpy(link_cmd,argv[bu_optind], 10);
break;
case 'w':
strncpy(wheel_cmd,argv[bu_optind], 10);
break;
default:
fprintf(stderr,"Unknown option: -m%c\n",*bu_optarg);
return(0);
}
bu_optind += 1;
break;
case 'c':
get_circumf = 1;
break;
default:
fprintf(stderr,"Unknown option: -%c\n",c);
return(0);
}
}
return(1);
}
void show_info(which)/* for debugging - -1:track 0:both 1:link*/
int which;
{
int i;
if (which <=0){
fprintf(stderr,"track length: %f\n",tracklen);
fprintf(stderr,"link length: %f\n",tracklen/num_links);
for (i=0;i<NW;i++){
fprintf(stderr,"wheel %d: %f %f %f %f %f %f\n",i,x[i].w.pos[0],x[i].w.pos[1],x[i].w.pos[2],x[i].w.rad,x[i].w.ang1,x[i].w.arc);
fprintf(stderr,"track %d: %f %f %f %f %f %f %f\n",i,x[i].t.pos1[0],x[i].t.pos1[1],x[i].t.pos1[2],x[i].t.dir[0],x[i].t.dir[1],x[i].t.dir[2],x[i].t.len);
fprintf(stderr,"slope %d: %f %f %f %f\n",i,x[i].s.dir[0],x[i].s.dir[1],x[i].s.dir[2],x[i].s.len);
}
}
/* if (which >= 0){
fprintf(stderr,"%d %f %f %f %f\n",count,position[0],position[1],position[2],y_rot);
}*/
}
+114
View File
@@ -0,0 +1,114 @@
.TH ANIM_KEYREAD 1 BRL/CAD
.SH NAME
anim_keyread - prepares key frames from the mged savekey command for interpolation
.SH SYNOPSIS
.B anim_keyread
.B [-y|z]
.B < key.file
.B > key.table
.SH DESCRIPTION
.I Anim_keyread
takes as input a file containing a series of keyframes
generated by the
.I mged
command `savekey', and produces a table containing
the same information, except that the view orientation matrix is
changed to a form that can be interpolated. The default form for the
orientation information is the quaternion.
For each such keyframe in the input file,
.I anim_keyread
will produce a
row in the output file containing the time, the viewsize, the position
of the camera, and the orientation of the camera, specified as a unit
quaternion in the order x, y, z, and w.
.SH OPTIONS
.TP
.B -y
Specify the orientation in terms of yaw, pitch, and roll.
.TP
.B -z
Specify the orientation as a rotation about the z-axis, y-axis,
and then x-axis, where the columns are in the order: x,y,z.
.SH EXAMPLES
The following is an example of a typical keyframe generated by the
`savekey' command. The time is 0, the viewsize is ten, the camera is at the
point (2.5,2.5,3.53) and the camera orientation is specified by a
matrix.
.nf
0.000000
1.000000000e+01
2.500000000e+00 2.500000000e+00 3.535533906e+00
-7.071067812e-01 7.071067812e-01 0.000000000e+00 0.000000000e+00
-5.000000000e-01 -5.000000000e-01 7.071067812e-01 0.000000000e+00
5.000000000e-01 5.000000000e-01 7.071067812e-01 0.000000000e+00
0.000000000e+00 0.000000000e+00 0.000000000e+00 1.000000000e+00
.fi
For the key frame shown above, the output would
be:
.sp
0.000000 10.000000 2.500000 2.500000 3.535534 0.146447 0.353553 0.853553 0.353553
.sp
The last four numbers define the desired orientation as a
quaternion.
.PP
With the
.B -y
option, the output would be:
.sp
0.000000 10.000000 2.500000 2.500000 3.535534 -135.000000 -45.000000 0.000000
.sp
Here, the last three numbers are the yaw, pitch, and roll,
which can be interpreted as follows: Imagine a camera at the origin
originally facing the positive x-direction, with the z-axis going up
and the y-axis positive to the left. The camera should be rotated
+roll degrees about the x-axis, -pitch degrees about the y-axis,
and +yaw degrees about the z-axis. In this case, the camera ends up
pointing down and to the right of its original position.
.PP
With the -z option, the output would be:
.sp
0.000000 10.000000 2.500000 2.500000 3.535534 -35.264390 30.000000 144.735610
.sp
The last three numbers are x, y, and z rotation angles.
The camera is considered to be originally on the z-axis, looking toward
the origin with the x-axis to the right and the y-axis going up. The
camera is rotated 144.7 degrees about the model's z-axis, then 30
degrees about the model's y-axis, and finally -35.2 degrees about the
model x-axis.
.SH DIAGNOSTICS
Problems arise when using Eulers angles, because
certain orientations do not have a uniqe representation, and the program
must arbitrarily select among an infinite number of possibilities. For
example, when using yaw, pitch and roll, the yaw and roll
become indistinguishable when the pitch is 90 degrees.
.PP
When this happens, the roll is set to 0, and the following
messages appear on standard error:
.nf
Warning: roll arbitrarily set to 0.0; yaw set to -0.585334 radians.
Warning: yaw and roll arbitrarily defined at time = 1.000000.
.fi
A similar effect occurs in xyz format when the rotation about
the y-axis is 90 degrees.
.nf
Warning: x arbitrarily set to 0.0; z set to 0.000000.
Warning: x and z rotations arbitrarily defined at time = 9.000000.
.fi
One nice thing about quaternions is that you don't run into such
problems.
.SH SEE ALSO
mged(1), tabsub(1), anim_script(1), tabinterp(1)
.SH AUTHOR
Carl J. Nuzman
.SH COPYRIGHT
This software is Copyright (C) 1993-2004 by the United States Army
in all countries except the USA. All rights reserved.
.SH "BUG REPORTS"
Reports of bugs or problems should be submitted via electronic
mail to <CAD@ARL.ARMY.MIL>.
+162
View File
@@ -0,0 +1,162 @@
/* A N I M _ K E Y R E A D . C
*
* Convert an list of mged-style 'savekey' keyframes into an
* animation table
*
* The output table specifies the orientation in one of three ways:
*
* default - quaternions in the order x, y, z, w.
*
* -z option - Eulers angles, in the order xyz. The model axes are
* considered to be rotated about the camera's z, y, and
* x axes (in that order).
*
* -y option - Eulers angles in the form yaw, pitch, roll.
*
* This is more or less a special case of anim_orient.c
*
* Author -
* Carl J. Nuzman
*
* Source -
* The U. S. Army Research Laboratory
* Aberdeen Proving Ground, Maryland 21005-5068 USA
*
* Distribution Notice -
* Re-distribution of this software is restricted, as described in
* your "Statement of Terms and Conditions for the Release of
* The BRL-CAD Pacakge" agreement.
*
* Copyright Notice -
* This software is Copyright (C) 1993-2004 by the United States Army
* in all countries except the USA. All rights reserved.
*/
#include "conf.h"
#include <stdio.h>
#include <math.h>
#include "machine.h"
#include "vmath.h"
#include "bu.h"
#ifndef M_PI
#define M_PI 3.14159265358979323846
#endif
#define YPR 0
#define XYZ 1
#define QUATERNION 2
#define DEGREES 0
#define RADIANS 1
#define NORMAL 0
#define ERROR1 1
#define ERROR2 2
#define DTOR M_PI/180.0
#define RTOD 180.0/M_PI
int mode;
int units;
extern int bu_optind;
extern char *bu_optarg;
int get_args();
extern void anim_v_unpermute();
int
main(argc,argv)
int argc;
char **argv;
{
int c;
fastf_t time, viewsize;
fastf_t eyept[3], viewrot[16], angle[3], quat[4];
int anim_mat2ypr(), anim_mat2zyx(), anim_mat2quat();
if (!get_args(argc,argv))
fprintf(stderr,"anim_keyread: get_args error");
while (!feof(stdin)){ /* read one keyframe */
scanf("%lf", &time);
scanf("%lf", &viewsize);
scanf("%lf %lf %lf", eyept, eyept+1, eyept+2);
/* read in transposed matrix */
scanf("%lf %lf %lf %lf", viewrot+0, viewrot+4, viewrot+8, viewrot+12);
scanf("%lf %lf %lf %lf", viewrot+1, viewrot+5, viewrot+9, viewrot+13);
scanf("%lf %lf %lf %lf", viewrot+2, viewrot+6, viewrot+10, viewrot+14);
scanf("%lf %lf %lf %lf", viewrot+3, viewrot+7, viewrot+11, viewrot+15);
if (feof(stdin)) break;
printf("%.10g\t%.10g\t%.10g\t%.10g\t%.10g\t", time, viewsize,
eyept[0], eyept[1], eyept[2]);
if (mode==YPR) {
anim_v_unpermute(viewrot);
c = anim_mat2ypr(angle,viewrot);
if (c==ERROR1)
fprintf(stderr,"Warning: yaw and roll arbitrarily defined at time = %f.\n",time);
else if (c==ERROR2)
fprintf(stderr,"Keyread: can't interpret matrix at time = %f.\n",time);
if (units == DEGREES)
VSCALE(angle,angle,RTOD);
printf("%.10g\t%.10g\t%.10g\n",angle[0],angle[1],angle[2]);
}
else if (mode==XYZ) {
c = anim_mat2zyx(angle,viewrot);
if (c==ERROR1)
fprintf(stderr,"Warning: x and z rotations arbitrarily defined at time = %f.\n",time);
else if (c==ERROR2)
fprintf(stderr,"Keyread: can't interpret matrix at time = %f\n.",time);
if (units == DEGREES)
VSCALE(angle,angle,RTOD);
printf("%.10g\t%.10g\t%.10g\n",angle[X],angle[Y],angle[Z]);
}
else if (mode==QUATERNION){
anim_mat2quat(quat,viewrot);
printf("%.10g\t%.10g\t%.10g\t%.10g\n",quat[X],quat[Y],quat[Z],quat[W]);
}
}
return( 0 );
}
#define OPT_STR "yzqr"
int get_args(argc,argv)
int argc;
char **argv;
{
int c;
mode = QUATERNION; /* default */
units = DEGREES;
while ( (c=bu_getopt(argc,argv,OPT_STR)) != EOF) {
switch(c){
case 'y':
mode = YPR;
break;
case 'z':
mode = XYZ;
break;
case 'q':
mode = QUATERNION;
break;
case 'r':
units = RADIANS;
break;
default:
fprintf(stderr,"Unknown option: -%c\n",c);
return(0);
}
}
return(1);
}
+58
View File
@@ -0,0 +1,58 @@
.TH ANIM_LOOKAT 1 BRL/CAD
.SH NAME
anim_lookat - create a view animation script or table which looks from an eye point to
a specified point.
.SH SYNOPSIS
.B anim_lookat
.B [\-f #]
.B \[-v]
.B < in.table
.B > out.script
.PP
.B anim_lookat
.B \-[y|q]
.B \[-v]
.B < in.table
.B > out.table
.SH DESCRIPTION
This program takes as input a seven-column animation table
consisting of time, an eye point, and a "look-at point", and prints a
view animation script to control the virtual camera.
The camera always remains "right-side up"; that is, it yaws and pitches but
doesn't roll. In cases where the camera looks vertically up or down, the
yaw from the previous frame is retained. This avoids sudden jumps as much
as possible.
.PP
.SH OPTIONS
.TP
.B \-f#
Specify an integer with which to begin
numbering frames. The default is 0.
.TP
.B \-y
The output will be an animation table rather
than a view animation script. The output table has 7 columns:
a time column, three
columns representing position, and three columns representing yaw,
pitch, and roll.
.TP
.B \-q
The output will be an animation table rather than a view animation script.
The output table has eight columns:
a time column, three position columns, and four columns
representing the x,y,z, and w coordinates of an orientation quaternion.
.TP
.B \-v
Include the viewsize in the output script or table. The viewsize is
calculated in every frame as twice the distance from the eye point to
the lookat point. If the output is a table, then the viewsize is printed
in the second column.
.SH AUTHOR
Carl J. Nuzman
.SH COPYRIGHT
This software is Copyright (C) 1993-2004 by the United States Army
in all countries except the USA. All rights reserved.
.SH "BUG REPORTS"
Reports of bugs or problems should be submitted via electronic
mail to <CAD@ARL.ARMY.MIL>.
+159
View File
@@ -0,0 +1,159 @@
/* A N I M _ L O O K A T . C
*
* Given animation tables for the position of the virtual camera
* and a point to look at at each time, this program produces an animation
* script to control the camera. The view is kept rightside up, whenever
* possible. When looking vertically up or down, the exact orientation
* depends on the previous orientation.
*
* Author -
* Carl J. Nuzman
*
* Source -
* The U. S. Army Research Laboratory
* Aberdeen Proving Ground, Maryland 21005-5068 USA
*
* Distribution Notice -
* Re-distribution of this software is restricted, as described in
* your "Statement of Terms and Conditions for the Release of
* The BRL-CAD Pacakge" agreement.
*
* Copyright Notice -
* This software is Copyright (C) 1993-2004 by the United States Army
* in all countries except the USA. All rights reserved.
*/
#include "conf.h"
#include <stdio.h>
#include <math.h>
#include "machine.h"
#include "vmath.h"
#include "anim.h"
#include "bu.h"
#ifndef M_PI
#define M_PI 3.14159265358979323846
#endif
#ifndef RTOD
#define RTOD (180/M_PI)
#endif
#define LOOKAT_SCRIPT 0
#define LOOKAT_YPR 1
#define LOOKAT_QUAT 2
extern int bu_optind;
extern char *bu_optarg;
int frame = 0;
int print_mode = LOOKAT_SCRIPT;
int print_viewsize = 0;
int get_args();
extern void anim_dirn2mat();
extern int anim_mat2ypr();
extern int anim_mat2quat();
int
main(argc,argv)
int argc;
char **argv;
{
fastf_t time, vsize=0.0;
vect_t eye,look,dir, angles, norm, temp;
quat_t quat;
mat_t mat;
int val = 0;
VSETALL(look,0.0);
VSETALL(eye,0.0);
if (argc > 1)
get_args(argc,argv);
VSET(norm, 0.0, 1.0, 0.0);
while (!feof(stdin)){
val=scanf("%lf %lf %lf %lf %lf %lf %lf",&time,eye,eye+1,eye+2,look,look+1,look+2);
if (val < 7){
break;
}
if (print_viewsize) {
VSUB2(temp, eye, look);
vsize = MAGNITUDE(temp);
vsize *= 2.0;
}
VSUBUNIT(dir,look,eye);
anim_dirn2mat(mat,dir,norm);
VSET(norm, mat[1],mat[5], 0.0);
switch (print_mode) {
case LOOKAT_SCRIPT:
printf("start %d;\n",frame++);
printf("clean;\n");
if (print_viewsize)
printf("viewsize %.10g;\n",vsize);
printf("eye_pt %.10g %.10g %.10g;\n",eye[0],eye[1],eye[2]);
printf("viewrot %.10g\t%.10g\t%.10g\t0\n", -mat[1], -mat[5], -mat[9]);
printf("%.10g\t%.10f\t%.10g\t0\n", mat[2], mat[6], mat[10]);
printf("%.10g\t%.10g\t%.10g\t0\n", -mat[0], -mat[4], -mat[8]);
printf("0\t0\t0\t1;\n");
printf("end;\n");
break;
case LOOKAT_YPR:
anim_mat2ypr(angles,mat);
angles[0] *= RTOD;
angles[1] *= RTOD;
angles[2] *= RTOD;
printf("%.10g",time);
if (print_viewsize)
printf("\t%.10g",vsize);
printf("\t%.10g\t%.10g\t%.10g",eye[0],eye[1],eye[2]);
printf("\t%.10g\t%.10g\t%.10g\n",angles[0],angles[1],angles[2]);
break;
case LOOKAT_QUAT:
anim_mat2quat(quat,mat);
printf("%.10g",time);
if (print_viewsize)
printf("\t%.10g",vsize);
printf("\t%.10g\t%.10g\t%.10g",eye[0],eye[1],eye[2]);
printf("\t%.10g\t%.10g\t%.10g\t%.10g\n",quat[0],quat[1],quat[2],quat[3]);
break;
}
}
return( 0 );
}
#define OPT_STR "f:yqv"
int get_args(argc,argv)
int argc;
char **argv;
{
int c;
while ( (c=bu_getopt(argc,argv,OPT_STR)) != EOF) {
switch(c){
case 'f':
sscanf(bu_optarg,"%d",&frame);
break;
case 'y':
print_mode = LOOKAT_YPR;
break;
case 'q':
print_mode = LOOKAT_QUAT;
break;
case 'v':
print_viewsize = 1;
break;
default:
fprintf(stderr,"Unknown option: -%c\n",c);
return(0);
}
}
return(1);
}
+97
View File
@@ -0,0 +1,97 @@
.TH ANIM_OFFSET 1 BRL/CAD
.SH NAME
anim_offset - create an animation table for an object rigidly attached to
another object.
.SH SYNOPSIS
.B anim_offset
.B -o # # #
.B [-r]
.B < in.table
.B > out.table
.SH DESCRIPTION
This filter operates on animation tables of the type used by
.I tabsub
and
.I anim_script.
Given a table specifying the position and
orientation of one object at every applicable time,
.I anim_offset
calculates
the position of another object which is rigidly attached to it.
.PP
The columns of the input table should be time, three columns of
position, followed by yaw, pitch, and roll. The output will be
normally be a four-column file specifying time and position. If the
.B -r
option is used, the output is a seven-column file in which the last
three columns are copies of the orientation information from the input
file.
.PP
The position of the object relative to the rigid body should be
given on the command line in the order x, y, z, with the
.B -o # # #
option. These offset values
should be as measured from the centroid of the rigid body.
.SH EXAMPLES
This filter could be used, for example, to do an animation where
the camera is placed inside a moving vehicle.
.PP
Suppose that truck.table contains the desired position of the
center of the front axle of the truck as well as its orientation at each
time. One row of the table might look like this:
.nf
35.2 12450 -140 600 90.0 0.0 0.0
.fi
Thus 35.2 seconds into the animation, the center of the front axle will
be at (12450, -140, 600), and the truck will be pointed in the positive
y direction. (yaw = 90).
.PP
Now, suppose we want the camera to ride along in the cab, above
and behind the front axle and somewhat to the left. To specify this
offset, we use the coordinate frame of the truck, with the origin at the
center of the front axle, the x-axis to the front, y to the left, and z
pointing up. Let the exact offset from the axle to the desired camera
position in this case be (-600, 900, 1200), in units of mm. Now we use
the routine:
.nf
anim_offset -o -600 900 1200 < truck.table > camera.table
.fi
The result is a four-column table giving the desired position of the
virtual camera at each time. The row corresponding to the sample row
above would be:
.nf
35.2 11550 -740 1800
.fi
With the
.B -r
option, the output would have been:
.nf
35.2 11550 -740 1800 90.0 0.0 0.0
.fi
Now
.I tabsub
and/or
.I anim_script
can be used to process these two animation
tables into an animation script.
.SH BUGS
The program will only use orientations specified as yaw,
pitch, and roll. You can get around this using
.IR anim_orient ,
which converts between different orientation representations.
.SH AUTHOR
Carl J. Nuzman
.SH COPYRIGHT
This software is Copyright (C) 1993-2004 by the United States Army
in all countries except the USA. All rights reserved.
.SH "BUG REPORTS"
Reports of bugs or problems should be submitted via electronic
mail to <CAD@ARL.ARMY.MIL>.
+110
View File
@@ -0,0 +1,110 @@
/* A N I M _ O F F S E T . C
*
* Animate an object which is rigidly attached to another.
*
* Given an animation table specifying the position and orientation of
* one object, anim_offset produces a similar table specifying the
* position of an object rigidly attached to it.
*
*
* Author -
* Carl J. Nuzman
*
* Source -
* The U. S. Army Research Laboratory
* Aberdeen Proving Ground, Maryland 21005-5068 USA
*
* Distribution Notice -
* Re-distribution of this software is restricted, as described in
* your "Statement of Terms and Conditions for the Release of
* The BRL-CAD Pacakge" agreement.
*
* Copyright Notice -
* This software is Copyright (C) 1993-2004 by the United States Army
* in all countries except the USA. All rights reserved.
*/
#include "conf.h"
#include <math.h>
#include <stdio.h>
#include "machine.h"
#include "vmath.h"
#include "bu.h"
#include "anim.h"
extern int bu_optind;
extern char *bu_optarg;
int full_print = 0;
vect_t offset;
int get_args();
extern void anim_dy_p_r2mat();
extern void anim_add_trans();
int
main(argc,argv)
int argc;
char **argv;
{
int val;
fastf_t yaw, pitch, roll, time;
vect_t temp,point,zero;
mat_t mat;
VSETALL( temp , 0.0 );
VSETALL( point , 0.0 );
VSETALL( zero , 0.0 );
(void) get_args(argc,argv);
while (1) {
/*read line from table */
val = scanf("%lf%*[^-0123456789]",&time); /*read time,ignore garbage*/
val = scanf("%lf %lf %lf", point, point+1, point +2);
val = scanf("%lf %lf %lf", &yaw, &pitch, &roll);
if (val < 3) {
break;
}
anim_dy_p_r2mat(mat,yaw, pitch,roll);
anim_add_trans(mat,point,zero);
MAT4X3PNT(temp,mat,offset);
printf("%.10g\t%.10g\t%.10g\t%.10g",time, temp[0], temp[1], temp[2]);
if (full_print)
printf("\t%.10g\t%.10g\t%.10g", yaw, pitch, roll);
printf("\n");
}
return( 0 );
}
#define OPT_STR "ro:"
int get_args(argc,argv)
int argc;
char **argv;
{
int c;
while ( (c=bu_getopt(argc,argv,OPT_STR)) != EOF) {
switch(c){
case 'r':
full_print = 1;
break;
case 'o':
sscanf(argv[bu_optind-1],"%lf",offset+0);
sscanf(argv[bu_optind],"%lf",offset+1);
sscanf(argv[bu_optind+1],"%lf",offset+2);
bu_optind += 2;
break;
default:
fprintf(stderr,"Unknown option: -%c\n",c);
return(0);
}
}
return(1);
}
+217
View File
@@ -0,0 +1,217 @@
.TH ANIM_ORIENT 1 BRL/CAD
.SH NAME
anim_orient - convert between orientation formats
.SH SYNOPSIS
.B anim_orient
.B [q|y|a|z|m][vri]
.B [q|y|a|z|m][vriu]
.B < in.table
.B > out.table
.SH DESCRIPTION
.I Anim_orient
is a filter which translates a table of orientation
information from one format to another. The method used is to convert
the input format to a matrix, then convert the matrix to the desired
output format. The input format is specified in the first argument, and
the output format is specified in the second.
The orientation formats
must be one of the following:
.B q
(quaternion),
.B y
(yaw,pitch, and roll),
.B a
(azimuth, elevation, and twist),
.B z
(x-y-z angles), or
.B m
(rotation matrix).
In addition, the output format may be modified by the
.B u
option, and the input and output formats may be modified by the
.BR r ,
.BR i ,
and
.B v
options. The
.B r
option specifies that angles are read or written in radians, rather
than degrees. The
.BR i , v ,
and
.B u
options are explained below.
.PP
To clearly understand the operation of anim_orient, it is important to
examine the difference between orientation and rotation.
The matrices, quaternions, and angles
used by anim_orient specify rotations. These are transformations
which, when applied to an object, preserve its shape but change its
orientation with respect to a fixed set of axes. Given the initial
orientation of an object, a rotation defines the final orientation, but
different initial orientations will yield different final orientations.
In order
to represent orientations with rotations, we
must define a default initial orientation for the object.
Then a given matrix, quaternion, or set of angles represents the orientation
resulting from applying the rotation to the initial object orientation.
.PP
If no modifying codes are specified, anim_orient assumes that the
default orientation of the object in question faces the positive
x-direction, with the world y-axis pointing to the object's left and the
z-axis pointing up. This is the orientation in which many
.I brlcad
objects
are modeled, and the default assumed by other animation routines such as
anim_script. If the
.B v
code is specified, then the default orientation
is taken to be facing the negative z-direction, with the world x-axis
pointing to the object's right and the y-axis pointing up. This is the
default orientation of the eye in
.I mged
and
.IR rt .
Some common uses of the v
option are demonstrated in the examples section.
.PP
The input and output format codes are:
.TP
.BR q :
Quaternions, in the order x,y,z,w. This is the default input and
output format. The output will
always be unit quaternions. For a unit quaternion, the
xyz-vector represents an axis of rotation and and w represents
cos(omega/2), where
omega is the angle to be rotated about the given axis.
.TP
.BR z :
x-y-z angles, in the order x, y, z. They represent a rotation
of z degrees around the z-axis, followed by y degrees around the y-axis,
followed by x degrees around the x-axis. If the code
.B zr
is used
then the angles will be read or written in radians
rather than degrees.
.TP
.BR y :
yaw-pitch-roll format, in that order. They represent
a rotation of +roll degrees about the x-axis, -pitch degrees about
the y-axis, followed by +yaw degrees about the z-axis. If the code
.B yr
is used, angles are in radians rather than degrees.
.TP
.BR a :
azimuth, elevation, twist, in that order. They represent a rotation of
-twist degrees about the x-axis, +elevation degrees about the y-axis,
and +azimuth + 180 degrees about the z-axis. Alternatively, they can
be thought of as a 180 degree rotation about the z-axis followed by a
rotation of +twist degrees about the x-axis, -elevation degrees about
the y-axis, and +azimuth degrees about the z-axis.
.TP
.BR m :
pre-multiplication rotation matrix. Sixteen
numbers form a 4x4 matrix, although only the nine elements in the upper
left corner are actually used. This is the format used at the interior of
the conversion routine. It is a transformation from initial orientation to
a new orientation.
.PP
The input and ouput modification codes are:
.TP
.B i
This code is used in conjunction with any of the format codes to represent
the inverse transformation. Under the
.B i
code, a matrix, quaternion, or
set of angles represents the inverse of the rotation that it normally
represents.
For example, normally, the orientation
corresponding to a given matrix is the orientation that the default
object ends up in after the matrix is applied to it. With the
.B i
code,
a given matrix represents the orientation an object should be placed
in so that the applying the matrix puts it back in the default
orientation.
One common use of the
.B i
option is for handling "Viewrot" matrices used
by
.I mged
and
.IR rt .
The viewrot matrix is a model-to-view matrix, which is
the transpose (inverse) of the matrix which would conceptually be
applied to an eye object to put it in the desired place in the model.
.TP
.B v
When this option is specified, the corresponding rotation is considered
applied to the default view orientation, rather than the default object
orientation, as explained above.
.TP
.B u
This option forces the output orientation to be upright, or "right-side
up", where the z-axis is the up direction. In terms of yaw, pitch, and
roll, this means that the roll is forced to zero. Because this is a
one-way operation, it can only be applied to the output orientation, not
the input.
.SH EXAMPLES
.sp
Normalize a table of quaternions to unit magnitude. (quaternions are the
default format).
.sp
anim_orient < in.table > out.table
.sp
change xyz angles to a rotation matrix
.sp
anim_orient z m < in.table > out.table
.sp
change azimuth,elevation, and twist to a matrix suitable for the
.I rt
viewrot command
.sp
anim_orient a miv < in.table > out.table
.sp
transpose matrices
.sp
anim_orient m mi < in.table > out.table
.sp
change radian xyz angles to yaw-pitch-roll in degrees
.sp
anim_orient zr y < in.table > out.table
.sp
given a quaternion being applied to an object facing the x-axis,
find the quaternion needed
to turn the virtual camera in the same direction using
.IR rt 's
orientation command
.sp
anim_orient q qv < in.table > out.table
.sp
Given the yaw, pitch, and roll of an object, find the yaw, pitch, and
roll which would bring it back to the default position.
.sp
anim_orient y yi < in.table > out.table
.sp
Force a table of view quaternions to represent "right-side up"
orientations.
.sp
anim_orient qv qvu < in.table > out.table
.SH BUGS
There are built-in trouble spots which occur, in ypr, xyz, or aet
formats, when the pitch, y-rotation, or elevation is an odd multiple of 90
degrees, because at this point the other two angles become
indistinguishable. The program makes the arbitrary assumption that the
roll is zero or that the x-rotation is zero, depending on the format,
and gives a warning to that effect on standard error.
.SH AUTHOR
Carl J. Nuzman
.SH COPYRIGHT
This software is Copyright (C) 1993-2004 by the United States Army
in all countries except the USA. All rights reserved.
.SH "BUG REPORTS"
Reports of bugs or problems should be submitted via electronic
mail to <CAD@ARL.ARMY.MIL>.
+290
View File
@@ -0,0 +1,290 @@
/* A N I M _ O R I E N T . C
*
* Convert between different orientation formats. The formats are:
* quaternion, yaw-pitch-roll, azimuth-elevation-twist, xyz angles,
* pre-multiplication rotation matrices, and transposed matrices (inverses).
* By default, the information is assumed to represent a transformation
* which should be an object which initially faces the x-axis, with the
* z-axis going up. Alternatively, the information can be interpreted as
* transformations which should be applied to an object initially facing the
* negative z-axis, with the y-axis going up.
* The conversion is done by converting each input form to a matrix,
* and then converting that matrix to the desired output form.
* Angles may be specified in radians or degrees.
*
* Author -
* Carl J. Nuzman
*
* Source -
* The U. S. Army Research Laboratory
* Aberdeen Proving Ground, Maryland 21005-5068 USA
*
* Distribution Notice -
* Re-distribution of this software is restricted, as described in
* your "Statement of Terms and Conditions for the Release of
* The BRL-CAD Pacakge" agreement.
*
* Copyright Notice -
* This software is Copyright (C) 1993-2004 by the United States Army
* in all countries except the USA. All rights reserved.
*/
#include "conf.h"
#include <stdlib.h>
#include <unistd.h>
#include <stdio.h>
#include <math.h>
#include "machine.h"
#include "vmath.h"
#ifndef M_PI
#define M_PI 3.14159265358979323846
#endif
#define YPR 0
#define XYZ 1
#define AET 2
#define QUAT 3
#define MAT 4
#define DEGREES 0
#define RADIANS 1
#define ANIM_NORMAL 0
#define ANIM_ERROR1 1
#define ANIM_ERROR2 2
#define DTOR M_PI/180.0
#define RTOD 180.0/M_PI
int parse_args();
extern void anim_y_p_r2mat();
extern void anim_tran();
extern void anim_v_unpermute();
extern void anim_dirn2mat();
extern void anim_v_permute();
extern int optind;
extern char *optarg;
int upright;
int input_mode, output_mode, length, input_units, output_units;
int input_perm, output_perm, input_inv, output_inv;
int
main(argc,argv)
int argc;
char **argv;
{
int num_read;
fastf_t temp[3], temp2[3],angle[3],quat[4],matrix[16];
void anim_zyx2mat(),anim_ypr2mat(),anim_quat2mat(), anim_mat_print();
int anim_mat2ypr(),anim_mat2zyx(),anim_mat2quat();
if(!parse_args(argc,argv)) {
fprintf(stderr,"Get_args error.\n");
exit(0);
}
/* read data */
num_read = length;
while (1){
switch (input_mode) {
case YPR:
case XYZ:
case AET:
num_read = scanf("%lf %lf %lf",angle,angle+1,angle+2);
/* convert to radians if in degrees */
if (input_units==DEGREES) {
VSCALE(angle,angle,DTOR);
}
break;
case QUAT:
num_read = scanf("%lf %lf %lf %lf", quat,quat+1,quat+2,quat+3);
break;
case MAT:
num_read = 0;
num_read += scanf("%lf %lf %lf %lf",matrix,matrix+1,matrix+2,matrix+3);
num_read += scanf("%lf %lf %lf %lf",matrix+4,matrix+5,matrix+6,matrix+7);
num_read += scanf("%lf %lf %lf %lf",matrix+8,matrix+9,matrix+10,matrix+11);
num_read += scanf("%lf %lf %lf %lf",matrix+12,matrix+13,matrix+14,matrix+15);
break;
}
if (num_read < length)
break;
/* convert to (object) matrix form */
switch (input_mode) {
case YPR:
anim_ypr2mat(matrix,angle);
break;
case AET:
anim_y_p_r2mat(matrix, angle[0]+M_PI, -angle[1],-angle[2]);
break;
case XYZ:
anim_zyx2mat(matrix,angle);
break;
case QUAT:
anim_quat2mat(matrix,quat);
break;
}
if (input_inv){
anim_tran(matrix);
}
if (input_perm){
anim_v_unpermute(matrix);
}
/* end of input conversion, begin output conversion*/
if (upright) { /* force right-side up */
VSET(temp, matrix[0], matrix[4], matrix[8]);
VSET(temp2, matrix[1], matrix[5], matrix[9]);
anim_dirn2mat(matrix,temp,temp2);
}
if (output_perm){
anim_v_permute(matrix);
}
if (output_inv){
anim_tran(matrix);
}
/* convert from matrix form and print result*/
switch (output_mode) {
case YPR:
anim_mat2ypr(angle,matrix);
if (output_units==DEGREES)
VSCALE(angle,angle,RTOD);
printf("%.12g\t%.12g\t%.12g\n",angle[0],angle[1],angle[2]);
break;
case AET:
anim_mat2ypr(angle,matrix);
if (angle[0] > 0.0) {
angle[0] -= M_PI;
} else {
angle[0] += M_PI;
}
angle[1] = -angle[1];
angle[2] = -angle[2];
if (output_units==DEGREES)
VSCALE(angle,angle,RTOD);
printf("%.12g\t%.12g\t%.12g\n",angle[0],angle[1],angle[2]);
break;
case XYZ:
anim_mat2zyx(angle,matrix);
if (output_units==DEGREES)
VSCALE(angle,angle,RTOD);
printf("%.12g\t%.12g\t%.12g\n",angle[0],angle[1],angle[2]);
break;
case QUAT:
anim_mat2quat(quat,matrix);
printf("%.12g\t%.12g\t%.12g\t%.12g\n",quat[0],quat[1],quat[2],quat[3]);
break;
case MAT:
anim_mat_print(stdout,matrix,0);
printf("\n");
}
}
return( 0 );
}
int parse_args(argc,argv)
int argc;
char **argv;
{
int c;
char *cp;
/* defaults */
upright = 0;
input_mode = QUAT;
output_mode = QUAT;
input_units = DEGREES;
output_units = DEGREES;
input_perm = 0;
output_perm = 0;
input_inv = 0;
output_inv = 0;
length = 4;
if (argc > 2) { /*read output mode */
cp = argv[2];
while ( (c=*cp++) ) {
switch (c) {
case 'q':
output_mode = QUAT;
break;
case 'y':
output_mode = YPR;
break;
case 'a':
output_mode = AET;
break;
case 'z':
output_mode = XYZ;
break;
case 'm':
output_mode = MAT;
break;
case 'i':
output_inv = 1;
break;
case 'r':
output_units = RADIANS;
break;
case 'v':
output_perm = 1;
break;
case 'u':
upright = 1;
break;
default:
fprintf(stderr,"anim_orient: unknown output option: %c\n",c);
return(0);
}
}
}
if (argc > 1) { /*read input mode */
cp = argv[1];
while ( (c=*cp++) ) {
switch (c) {
case 'q':
input_mode = QUAT;
length = 4;
break;
case 'y':
input_mode = YPR;
length = 3;
break;
case 'a':
input_mode = AET;
length = 3;
break;
case 'z':
input_mode = XYZ;
length = 3;
break;
case 'm':
input_mode = MAT;
length = 16;
break;
case 'i':
input_inv = 1;
break;
case 'r':
input_units = RADIANS;
break;
case 'v':
input_perm = 1;
break;
default:
fprintf(stderr,"anim_orient: unknown input option: %c\n",c);
return(0);
}
}
}
return(1);
}
+339
View File
@@ -0,0 +1,339 @@
.TH ANIM_SCRIPT 1 BRL/CAD
.SH NAME
anim_script - make an animation script for one object
.SH SYNOPSIS
.B anim_script
.B [-v #]
.B [-r|t|s]
.B [-q][-p]
.B [-a|b # # #]
.B [-c|d # # #]
.B [-f #]
.B [-m cmd]
.B [objectname]
.B < in.table
.B > out.script
.SH DESCRIPTION
.I Anim_script
is designed to produce an animation script for the
animation of the virtual camera or one
.I brlcad
object at a time. It is
complementary to
.I tabsub
in that it performs a similar
function, but with a different philosophy.
.PP
Both
.I anim_script
and
.I tabsub
use one row of an animation table to
produce one frame of an animation script. With
.I tabsub,
the user supplies
a template file which controls the form of the animation frames. This
allows the maximum user control, but also requires a good understanding
of the script format. With
.I anim_script,
the user supplies all the necessary
information on the command line. The range of possible output scripts is
limited, but the user does not have to deal directly with the details.
Both routines have special features which make certain common situations
easy to do. One of the most important special features of
.I anim_script
is the
ability to specify a reference position and orientation, as explained
below.
.PP
The objectname is the name of the object which is to be
animated, as it will appear in the ouput script. For example, if
"hatch1"
is a member of "turret" which is a member of "tank" which is one of the
objects specified on the command line of the call to
.I rt,
then the objectname "tank/turret/hatch1" or simply "turret/hatch1" would be used to
animate the hatch. The tank itself would be referred to by the name,
"/tank". Note that toplevel objects should be preceeded by a slash.
If view animation is being performed, no objectname
should be included.
.PP
.B in.table
should be a seven-column animation table,
specifying the time, 3d position, yaw, pitch and roll of the
object (or camera), although this changes if the
.BR -r ,
.BR -t ,
.BR -s ,
or
.B -v#
options are used.
.SH OPTIONS
.TP
.B \-r
.B in.table
is a four-column file including time and rotation
information only. No translation will occur.
.TP
.B \-t
.B in.table
is a four-column file including time and translation
information only. No rotation will occur.
.TP
.B \-s
.B in.table
is a four-column file including time and translation
information only. The vehicle will be rotated (steered) to face the
direction of motion.
.TP
.B \-q
Quaternion orientation. Any orientation information in
.B in.table
will be in quaternion form, in the order x,y,z,w. The identity quaternion
representing no orientation change is (0,0,0,1).
.TP
.B \-p
Permuted orientation. This option indicates that transformations defined by
the quaternions should be applied to an object which has first been placed
in
.IR rt 's
default eye orientation. Thus, the identity quaternion represents yawing the
object 90 degrees to the left and then pitching it 90 degrees downward.
The quaternions produced by
.IR mged 's
saveview command and used by
.IR rt 's
orientation command
are quaternions of this type. See
.I anim_orient
for more information.
.TP
.B \-v#
The desired output is a view animation script, rather
than an object animation script. No object should be specified. The
argument can be any floating point number. If
the argument
is positive, the command:
.sp
viewsize #;
.sp
will be placed at the beginning of the ouput file. If it is
zero, the `viewsize' command is omitted from the output script. If it is
negative, then the
viewsize for each frame is expected to be in the first column after the
time in
.BR in.table .
A `viewsize' command would then be
included immediately after the `start' command of each frame.
.TP
.B \-f#
Specify the integer with which to begin
numbering the frames of the output script. The default is 0.
.PP
The remaining options give information about the object which is
to be animated.
.TP
.B \-a # # #
or
.TP
.B \-b # # #
These options take three arguments, which are the
yaw, pitch, and roll of the object's axes with respect to the
world axes. With
.B \-a,
rotations specified in the infile will be applied
with respect to the object's axes. With the
.B \-b
option, the object is
rotated so that its axes coincide with the world axes, and then all
rotations and translations are carried out with respect to the world
axes. The
.B \-b
option is particularly useful in conjunction with the
.B \-s
option, because it tells
.I anim_script
which way the front of the vehicle faces. See
the examples below.
.TP
.B \-c # # #
or
.TP
.B \-d # # #
These options take three arguments, which are the x, y,
and z coordinates of the point which is to be considered the "centroid"
of the object. All rotations will occur about this point. If
.B \-c
is used,
translations from the input table will be considered to be relative
displacements from this point. If
.B \-d
is used, the translations in the
input table will be interpreted as absolute displacement from the world
origin. The direction of translation in both cases is along the world
axes, unless the
.B \-a
option has been used, in which case the
translations are with respect to the object's axes. See the examples below.
.PP
When the
.B \-v
option is used, the virtual camera is the object
being animated, and so the meaning of the preceeding four options
changes somewhat. The
.B \-c
and
.B \-a
options are not useful in this context.
The
.B \-d
option can be thought of as specifying the position and
orientation of a virtual
tripod with respect to the camera lens. The translations and rotations
specified in
the input table will be applied to the tripod, to which the camera is
rigidly attached. For example, the option
.B \-d 10 0 \-2
in conjunction with
the
.B \-v#
option means that the virtual tripod is 10 units in front of the
camera and 2
units below the camera's line of sight. The option
.B \-b -90 0 0
in this
context would mean that the front of the virtual tripod faces 90 degrees
to the right of the virtual camera. As translation and rotation
information are read in from in.table, they are applied to the virtual
tripod, with the virtual camera rigidly attached. See below for examples
of how this might be used.
.TP
.B -m cmd
Specify a matrix command to use in, object animation. The default value
is "lmul", which means that matrices in the output script are
multiplied onto the
left of the matrix between the object being animated and its parent.
The matrix residing between the object and its parent is referred to as
the current arc. The possible matrix commands are the following:
.nf
lmul - left-multiply the matrix onto the current arc
rmul - right-multiply the matrix onto the current arc
rarc - replace the current arc with the matrix
rstack - replace the stack of ancestor matrices with the matrix
rboth - replace the current arc with the matrix and replace the
stack of ancestor matrices with the identity matrix.
.fi
This option is intended primarily to give expert users additional
flexibility, and shouldn't be needed by most animators.
.SH EXAMPLES
To animate a truck which is modeled with the front facing the positive
x-direction, the position of the center of the truck and its orientation at
each time should be in
.BR truck.table .
If the center of the modeled truck is at
the point (234,0,1200) then the following command could be used:
.sp
anim_script -d 234 0 1200 /truck < truck.table > truck.script.
.sp
If the front of the model truck faces (for some reason)
halfway
between the x and y axes, a
.B \-b
option is added, to show the relationship
between world and truck axes:
.sp
anim_script -b 45 0 0 -d 234 0 1200 /truck < truck.table > truck.script.
.sp
To steer the truck automatically to face the direction of motion,
the
.B \-s
option is added, and the orientation columns should be removed from
.BR truck.table .
.sp
anim_script -s -b 45 0 0 -d 234 0 1200 /truck < truck.table > truck.script.
.sp
.sp
Animating a steering wheel: Suppose the steering wheel is stored
in the database so that the axis it turns on is at an yaw of -135
degrees and an pitch of 30 degrees. It passes through the point
(700,800,2400). Then we select "rotation only" with
.B \-r
and specify the
relationship between the steering wheels axes and the world with the
.B \-a
and
.B \-c
options. In
.B roll.table
we put the time, two zero columns, and a
column specifying the roll of the wheel (How much it is to be twisted).
.sp
anim_script -r -a -135 30 0 -c 700 800 2400 truck/steering_column/wheel <
roll.table > steer.table
.sp
Alternativly, if the turning of the wheel was stored in the yaw
(second) column of a file,
.BR turn.table ,
a different set of axes would be
used to achieve the same effect:
.sp
anim_script -r -a 45 60 0 -c 700 800 2400 truck/steering_column/wheel <
turn.table > steer.table
.sp
.PP
To animate seven little men doing simultaneous backflips in different
places, you would want to use relative motion. That is, a translation
vector of (0,0,1) means move one unit upward, instead of move to the
point (0,0,1). For each little man, we specify his position in the
model using the
.B \-c
option. Then we can use the same backflip instuctions
for each of the little men.
.sp
anim_script -c 12 34 5 /little.man.one < generic.backflip.table >
little.man.one.script
.sp
anim_script -c -3 13 5 /little.man.two < generic.backflip.table >
little.man.two.script
.sp
and so on.
.sp
.sp
.SS Camera examples
If we know the desired postion of the camera and its orientation
at each time, it's very simple. The
.B -v#
option indicates that the view is
being animated; no object is specified.
.sp
anim_script -v0 < view.table > view.script
.sp
To follow a truck, so that the camera is always ten units behind and 4
units above it, we specify a virtual tripod in front of and below the
camera:
.sp
anim_script -v0 -d 10 0 -4 < truck.table > view.script
.sp
To do the same thing but with the camera turned to look at the right
side of the truck, we specify that the virtual tripod originally faces
to the right, so that the camera faces its right side. Thus when the
virtual tripod is placed in the same position and orientation as the
truck, the camera will be looking at the right side of the
truck.
.sp
anim_script -v0 -d 10 0 -4 -b -90 0 0 < truck.table > view.script
.SH BUGS
The reading of command line options which take more than one
argument are somewhat finicky. For example, it understands the
option "-d 1 1 1" but not "-d1 1 1".
.SH AUTHOR
Carl J. Nuzman
.SH COPYRIGHT
This software is Copyright (C) 1993-2004 by the United States Army
in all countries except the USA. All rights reserved.
.SH "BUG REPORTS"
Reports of bugs or problems should be submitted via electronic
mail to <CAD@ARL.ARMY.MIL>.
+272
View File
@@ -0,0 +1,272 @@
/* A N I M _ S C R I P T . C
*
* Turn an animation table into an animation script suitable for
* use by rt. Anim_script.c makes a script for one object at a time (or the
* virtual camera). Some of the available options include rotation
* only, translation only, automatic steering, and specifying reference
* coordinates.
*
* Author -
* Carl J. Nuzman
*
* Source -
* The U. S. Army Research Laboratory
* Aberdeen Proving Ground, Maryland 21005-5068 USA
*
* Distribution Notice -
* Re-distribution of this software is restricted, as described in
* your "Statement of Terms and Conditions for the Release of
* The BRL-CAD Pacakge" agreement.
*
* Copyright Notice -
* This software is Copyright (C) 1993-2004 by the United States Army
* in all countries except the USA. All rights reserved.
*/
#include "conf.h"
#ifdef USE_STRING_H
#include <string.h>
#else
#include <strings.h>
#endif
#include <math.h>
#include <stdio.h>
#include "machine.h"
#include "vmath.h"
#include "bu.h"
#include "bn.h"
#include "anim.h"
#ifndef M_PI
#define M_PI 3.14159265358979323846
#endif
int get_args();
extern int anim_steer_mat();
extern void anim_quat2mat();
extern void anim_v_unpermute();
extern void anim_mat_print();
extern int bu_optind;
extern char *bu_optarg;
/* info from command line args */
int relative_a, relative_c, axes, translate, quaternion, rotate;/*flags*/
int steer, view, readview, permute; /* flags*/
int first_frame;
fastf_t viewsize;
vect_t centroid, rcentroid, front;
mat_t m_axes, m_rev_axes; /* rotational analogue of centroid */
char mat_cmd[10]; /* default is lmul */
int
main(argc,argv)
int argc;
char **argv;
{
void anim_dx_y_z2mat(), anim_add_trans();
fastf_t yaw, pitch, roll;
vect_t point, zero;
quat_t quat;
mat_t a, m_x;
int val, go, frame, last_steer;
frame=last_steer=go=view=relative_a=relative_c=axes=0;
VSETALL(centroid,0);
VSETALL(rcentroid,0);
VSETALL(front,0);
VSETALL(point,0);
VSETALL(zero,0);
yaw = pitch = roll = 0.0;
MAT_IDN(m_axes);
MAT_IDN(m_rev_axes);
MAT_IDN(a);
if (!get_args(argc,argv))
fprintf(stderr,"anim_script: Get_args error\n");
frame = (steer) ? first_frame -1 : first_frame;
if (view && (viewsize > 0.0))
printf("viewsize %.10g;\n", viewsize);
while (1) {
/* read one line of table */
val = scanf("%*f"); /*ignore time */
if (readview)
scanf("%lf",&viewsize);
if(translate)
val=scanf("%lf %lf %lf", point, point+1, point+2);
if(rotate&&quaternion){
val = scanf("%lf %lf %lf %lf", quat,quat+1,quat+2,quat+3);
val -= 1;
} else if (rotate) {
val=scanf("%lf %lf %lf",&yaw,&pitch,&roll);
}
if (val < 3){ /* ie. scanf not completely successful */
/* with steering option, must go extra loop after end of file */
if (steer && !last_steer)
last_steer = 1;
else break;
}
/* calculate basic rotation matrix a */
if (steer)
go = anim_steer_mat(a,point,last_steer); /* warning: point changed by anim_steer_mat */
else if (quaternion) {
anim_quat2mat(a,quat);
go = 1;
} else {
anim_dx_y_z2mat(a,roll,-pitch,yaw);/* make ypr matrix */
go = 1;
}
/* if input orientation (presumably from quaternion) was
* designed to manipulate the view, first move the object
* to the default object position */
if (permute)
anim_v_unpermute(a);
/* make final matrix, including translation etc */
if (axes){ /* add pre-rotation from original axes */
bn_mat_mul(m_x,a,m_rev_axes);
MAT_MOVE(a,m_x);
}
anim_add_trans(a,point,rcentroid); /* add translation */
if (axes && relative_a){ /* add post-rotation back to original axes */
bn_mat_mul(m_x,m_axes,a);
MAT_MOVE(a,m_x);
}
if (relative_c)
anim_add_trans(a,centroid,zero); /* final translation */
/* print one frame of script */
if (go && view){
printf("start %d;\n", frame);
printf("clean;\n");
if (readview)
printf("viewsize %.10g;\n", viewsize);
printf("eye_pt %.10g %.10g %.10g;\n",a[3],a[7],a[11]);
/* implicit anim_v_permute */
printf("viewrot %.10g %.10g %.10g 0\n",-a[1],-a[5],-a[9]);
printf("%.10g %.10g %.10g 0\n", a[2], a[6], a[10]);
printf("%.10g %.10g %.10g 0\n", -a[0], -a[4],-a[8]);
printf("0 0 0 1;\n");
printf("end;\n");
}
else if (go){
printf("start %d;\n", frame);
printf("clean;\n");
printf("anim %s matrix %s\n", *(argv+bu_optind), mat_cmd);
anim_mat_print(stdout,a,1);
printf("end;\n");
}
frame++;
}
return( 0 );
}
#define OPT_STR "a:b:c:d:f:m:pqrstv:"
int get_args(argc,argv)
int argc;
char **argv;
{
int c, i, yes;
double yaw,pch,rll;
void anim_dx_y_z2mat(), anim_dz_y_x2mat();
rotate = translate = 1; /* defaults */
quaternion = permute = 0;
strcpy(mat_cmd, "lmul");
while ( (c=bu_getopt(argc,argv,OPT_STR)) != EOF) {
i=0;
switch(c){
case 'a':
bu_optind -= 1;
sscanf(argv[bu_optind+(i++)],"%lf", &yaw );
sscanf(argv[bu_optind+(i++)],"%lf", &pch );
sscanf(argv[bu_optind+(i++)],"%lf", &rll );
bu_optind += 3;
anim_dx_y_z2mat(m_axes, rll, -pch, yaw);
anim_dz_y_x2mat(m_rev_axes, -rll, pch, -yaw);
axes = 1;
relative_a = 1;
break;
case 'b':
bu_optind -= 1;
sscanf(argv[bu_optind+(i++)],"%lf", &yaw );
sscanf(argv[bu_optind+(i++)],"%lf", &pch );
sscanf(argv[bu_optind+(i++)],"%lf", &rll );
bu_optind += 3;
anim_dx_y_z2mat(m_axes, rll, -pch, yaw);
anim_dz_y_x2mat(m_rev_axes, -rll, pch, -yaw);
axes = 1;
relative_a = 0;
break;
case 'c':
bu_optind -= 1;
sscanf(argv[bu_optind+(i++)],"%lf",centroid);
sscanf(argv[bu_optind+(i++)],"%lf",centroid+1);
sscanf(argv[bu_optind+(i++)],"%lf",centroid+2);
bu_optind += 3;
VREVERSE(rcentroid,centroid);
relative_c = 1;
break;
case 'd':
bu_optind -= 1;
sscanf(argv[bu_optind+(i++)],"%lf",centroid);
sscanf(argv[bu_optind+(i++)],"%lf",centroid+1);
sscanf(argv[bu_optind+(i++)],"%lf",centroid+2);
bu_optind += 3;
VREVERSE(rcentroid,centroid);
relative_c = 0;
break;
case 'f':
sscanf(bu_optarg,"%d",&first_frame);
break;
case 'm':
strncpy(mat_cmd,bu_optarg, 10);
break;
case 'p':
permute = 1;
break;
case 'q':
quaternion = 1;
break;
case 'r':
rotate = 1;
translate = 0;
break;
case 's':
steer = 1;
relative_a = 0;
rotate = 0;
translate = 1;
break;
case 't':
translate = 1;
rotate = 0;
break;
case 'v':
yes = sscanf(bu_optarg,"%lf",&viewsize);
if (!yes) viewsize = 0.0;
if (viewsize < 0.0)
readview = 1;
view = 1;
break;
default:
fprintf(stderr,"Unknown option: -%c\n",c);
return(0);
}
}
return(1);
}
+143
View File
@@ -0,0 +1,143 @@
.TH ANIM_SORT 1 BRL/CAD
.SH NAME
anim_sort - combine concatenated animation scripts into one script
.SH SYNOPSIS
.B anim_sort
.B [-ic]
.B < mixed.script
.B > ordered.script
.SH DESCRIPTION
Note:
.I anim_sort
has been preempted in release 5.0 by
.IR scriptsort ,
which sorts scripts much faster.
.PP
.I Anim_sort
allows the user to combine several animation scripts
into a single script suitable for input to
.IR rt .
A convenient way to
prepare a complicated animation script is to develop each part
separately and then use
.I anim_sort
to combine the various parts. For
example, suppose that
.B view.script
is an animation script controlling the
movement of the virtual camera and the lighting,
.B mill.script
rotates
the blades of a windmill, and
.B quixote.script
controlls the movement of a
knight. These scripts should first be concatenated together:
.sp
cat view.script mill.script quixote.script > mixed.script
.sp
Calling
.I anim_sort
with
.B mixed.script
on standard input would
reorder the commands in
.B mixed.script
to make a viable script on standard
output.
.sp
Each of the input files to be concatenated is expected to be a
viable
.I rt
animation script, containing a series of frames of the
following form:
.sp
.nf
start framenumber;
any number of semi-colon terminated commands for rt;
end;
any number of post-raytracing commands
.fi
.sp
.I Anim_sort
reads the framenumber of the first start command, and uses
this to as the first frame number of the output file. The commands of
all frames in
.B mixed.script
with that framenumber are combined in the
ouput frame. The post-raytracing commands following all frames with that
framenumber are placed after the
.B end;
command of the output frame. This process is continued for each
successive integer,
until anim_sort reaches a framenumber which is not included in any of
the original scripts.
.sp
For example, if
.B view.script
contained frames numbered from 5 to
20,
.B mill.script
contained frames from 0 to 10, and
.B quixote.script
contained frames numbered from 15 to 25, the output script would start
at frame 5 (since
.B view.script
comes first in
.B mixed.script
) and end with
frame 25 (since frames 5 through 25 can be found somewhere in
.B mixed.script
). If the user wanted to include frames 0 through 4, which
are found only in
.B mill.script
, then
.B mill.script
should be concatenated
onto the beginning of
.B mixed.script
instead of the middle. In the
majority of animation situations, all of the input scripts would have
identical frame numbers anyway.
.sp
The first input script may also contain some lines preceeding
the first start command, which are copied to the beginning of the output
script. This is useful for commands such as 'viewsize', which are often
specified before the sequence of animations begins.
.sp
.SH OPTIONS
.TP
.B \-i
Incremental mode. The frames of the output script are printed in a scrambled
order which incrementally increases the time resolution of the animation.
For example, the frames of an eight-frame script would be printed in the
order: 0 4 2 6 1 3 5 7.
.TP
.B \-c
For most animation purposes, it is desirable to have a
.B clean
command immediately following the
.B start
command of each frame. The
default behavior of
.I anim_sort
is to include one
.B clean
command following the
.B start
command of each frame.
.B clean
commands from the input files are ignored. If the
.B -c
flag is activated, then no clean
commands are printed.
.SH SEE ALSO
rt(1), tabsub(1), anim_script(1)
.SH AUTHOR
Carl J. Nuzman
.SH COPYRIGHT
This software is Copyright (C) 1993-2004 by the United States Army
in all countries except the USA. All rights reserved.
.SH "BUG REPORTS"
Reports of bugs or problems should be submitted via electronic
mail to <CAD@ARL.ARMY.MIL>.
+188
View File
@@ -0,0 +1,188 @@
/* A N I M _ S O R T . C
*
* Combine multiple animation scripts on standard input into a
* single script on standard output. The output can be in natural order
* or in a scrambled order for incrementally increasing time
* resolution (-i option).
*
*
* Author -
* Carl J. Nuzman
*
* Source -
* The U. S. Army Research Laboratory
* Aberdeen Proving Ground, Maryland 21005-5068 USA
*
* Distribution Notice -
* Re-distribution of this software is restricted, as described in
* your "Statement of Terms and Conditions for the Release of
* The BRL-CAD Pacakge" agreement.
*
* Copyright Notice -
* This software is Copyright (C) 1993-2004 by the United States Army
* in all countries except the USA. All rights reserved.
*/
#include "conf.h"
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include "machine.h"
#include "externs.h"
#include "bu.h"
#define MAXLEN 50 /*maximum length of lines to be read */
#define MAXLINES 30 /* maximum length of lines to be stored*/
int suppressed; /* flag: suppress printing of 'clean;' commands */
int incremental; /* flag: order for incremental time resolution */
int get_args();
int
main(argc, argv)
int argc;
char **argv;
{
int length,frame_number, number, success, maxnum;
int first_frame,spread,reserve;
long last_pos;
char line[MAXLEN];
char pbuffer[MAXLEN*MAXLINES];
if (!get_args(argc,argv))
fprintf(stderr,"Get_args error\n");
/* copy any lines preceeding the first "start" command */
last_pos = ftell(stdin);
while (fgets(line,MAXLEN,stdin)!=NULL){
if (strncmp(line,"start",5)){
printf("%s",line);
last_pos = ftell(stdin);
}
else
break;
}
/* read the frame number of the first "start" command */
sscanf( strpbrk(line,"0123456789"),"%d", &frame_number);
/* find the highest frame number in the file */
maxnum = 0;
while(fgets(line,MAXLEN,stdin)!=NULL){
if(!strncmp(line,"start",5)){
sscanf(strpbrk(line,"0123456789"),"%d",&number);
maxnum = (maxnum>number)?maxnum:number;
}
}
length = maxnum - frame_number + 1;
/* spread should initially be the smallest power of two larger than
* or equal to length */
spread = 2;
while (spread < length)
spread = spread<<1;
first_frame = frame_number;
success = 1;
while (length--){
number = -1;
success = 0; /* tells whether or not any frames have been found which have the current frame number*/
if (incremental){
fseek(stdin, 0L, 0);
} else {
fseek(stdin, last_pos, 0);
}
reserve = MAXLEN*MAXLINES;
pbuffer[0] = '\0'; /* delete old pbuffer */
/* inner loop: search through the entire file for frames */
/* which have the current frame number */
while (!feof(stdin)){
/*read to next "start" command*/
while (fgets(line,MAXLEN,stdin)!=NULL){
if (!strncmp(line,"start",5)){
sscanf( strpbrk(line,"0123456789"),"%d", &number);
break;
}
}
if (number==frame_number){
if (!success){ /*first successful match*/
printf("%s",line);
if (!suppressed) printf("clean;\n");
success = 1;
last_pos = ftell(stdin);
}
/* print contents until next "end" */
while (fgets(line,MAXLEN,stdin)!=NULL){
if (!strncmp(line,"end;",4))
break;
else if (strncmp(line,"clean",5))
printf("%s",line);
}
/* save contents until next "start" */
while (fgets(line,MAXLEN,stdin)!=NULL){
if(!strncmp(line,"start",5))
break;
else {
reserve -= strlen(line);
reserve -= 1;
if (reserve > 0){
strncat(pbuffer,line,MAXLEN);
strcat(pbuffer,"\n");
}
}
}
}
}
if (success)
printf("end;\n");
/* print saved-up post-raytracing commands, if any */
printf("%s",pbuffer);
/* get next frame number */
if (incremental){
frame_number = frame_number + 2*spread;
while (frame_number > maxnum){
spread = spread>>1;
frame_number = first_frame + spread;
}
} else {
frame_number += 1;
}
}
return( 0 );
}
#define OPT_STR "ci"
int get_args(argc,argv)
int argc;
char **argv;
{
int c;
suppressed = 0;
while ( (c=bu_getopt(argc,argv,OPT_STR)) != EOF) {
switch(c){
case 'c':
suppressed = 1;
break;
case 'i':
incremental = 1;
break;
default:
fprintf(stderr,"Unknown option: -%c\n",c);
return(0);
}
}
return(1);
}
+89
View File
@@ -0,0 +1,89 @@
.TH ANIM_TIME 1 BRL/CAD
.SH NAME
anim_time - estimate appropriate time parameters for path
.SH SYNOPSIS
.B anim_time
.B [-s start_speed (absolute)]
.B [-e end_speed (absolute)]
.B [-i initial_speed (relative)]
.B [-f final_speed (relative)]
.B [-m max_len]
.B [-v|q]
.B < in.table
.B > out.table
.SH DESCRIPTION
This filter is designed to estimate appropriate time parameters for
an animation curve in 3D space. Given a four-column table specifying
time and 3D position for an object,
.I anim_time
ignores all but the first and last time specifications and
calculates reasonable time values for each intermediate point in the table.
The
output time values are based on the distances between points and the
calculated speed of the object. Various options allow the user to
control the assumptions on the object's initial and final speeds, and the
form of the output.
.I Anim_time
is intended to be used in situations where the user knows what key points
an object should pass through and how long the entire motion should take,
but doesn't care exactly when the object
reaches each point. It is also useful for getting objects to accelerate
smoothly to and from rest.
.SH OPTIONS
.TP
.BR -m #
Specify the maximum number of points to be read. This default to 64, so
you must use this option if you want to use tables with more than 64
points.
.TP
.BR -s #
Specify the starting speed of the object. If this option is not
specified, then the object is assumed to be initially travelling on a
pace to negotiate the entire path in the given time at a constant rate.
The argument must be positive and no greater than three times the speed
needed to traverse the path at a constant rate.
.TP
.BR -e #
Specify the final speed of the object. If this option is not specified,
then the object is assumed to end up travelling on a pace to negotiate
the entire path in the given time at a constant rate. The argument must
be positive and no greater than three times the speed needed to traverse
the path at a constant rate.
.TP
.BR -i #
Specify the initial speed of the object, relative to the speed that
would negotiate the given path at a constant rate. For example, an
argument of 2.0 means twice the speed needed to traverse the path at a
constant rate. Must lie between 0.0 and 3.0.
.TP
.BR -f #
Specify the final speed of the object, relative to the speed that would
negotiate the given path at a constant rate. Must lie between 0.0 and
3.0.
.TP
.B -v
Verbose option. The output table will contain a time column and three
position columns. If this option is not specified, only the new time
column will be printed.
.TP
.B -q
Query the total distance. If this option is specified, the only output
will be a number representing the total length of the input path.
.SH BUGS
The algorithm fits a cubic polynomial to the distance vs time graph, and then
uses Newton's method to find the times corresponding to each given distance.
If for some reason convergence is not reached,
.I anim_time
will print a warning on standard error. If the
.B -d
option is specified, the results of each iteration will be printed.
.SH AUTHOR
Carl J. Nuzman
.SH COPYRIGHT
This software is Copyright (C) 1996-2004 by the United States Army
in all countries except the USA. All rights reserved.
.SH "BUG REPORTS"
Reports of bugs or problems should be submitted via electronic
mail to <CAD@ARL.ARMY.MIL>.
+287
View File
@@ -0,0 +1,287 @@
/* A N I M _ T I M E . C
*
* Given an animation path consiting of time stamps and 3-d points,
* estimate new time stamps based on the distances between points, the
* given starting and ending times, and optionally specified starting
* and ending velocities.
*
* Author -
* Carl J. Nuzman
*
* Source -
* The U. S. Army Research Laboratory
* Aberdeen Proving Ground, Maryland 21005-5068 USA
*
* Distribution Notice -
* Re-distribution of this software is restricted, as described in
* your "Statement of Terms and Conditions for the Release of
* The BRL-CAD Pacakge" agreement.
*
* Copyright Notice -
* This software is Copyright (C) 1993-2004 by the United States Army
* in all countries except the USA. All rights reserved.
*/
#include "conf.h"
#include <math.h>
#include <stdio.h>
#include "machine.h"
#include "externs.h"
#include "vmath.h"
#include "bu.h"
#include "raytrace.h"
extern int bu_optind;
extern char *bu_optarg;
#define MAXLEN 64
#define DIVIDE_TOL (1.0e-10)
#define MAXITS 100
#define DELTA (1.0e-6)
#define TIME_NONE 0
#define TIME_ABSOLUTE 1
#define TIME_RELATIVE 2
/* command line variables */
fastf_t inv0,inv1;
int v0_set = TIME_NONE;
int v1_set = TIME_NONE;
int query = 0;
int verbose = 0;
int maxlines = 0;
int domem = 0;
int debug = 0;
int get_args();
fastf_t
gettime(dist, a, b, c, init)
fastf_t dist;
fastf_t a;
fastf_t b;
fastf_t c;
fastf_t init;
{
fastf_t old,new,temp;
int countdown,success;
countdown = MAXITS;
old = init;
success = 0;
while(countdown-->0){
temp = (3.0*a*old+2.0*b)*old+c;
if (temp<DIVIDE_TOL){
new = 0.75*old;
} else {
new = old - (((a*old+b)*old+c)*old-dist)/temp;
}
if (((new-old)<DELTA)&&((old-new)<DELTA)){
success = 1;
break;
}
if (debug)
printf("c: %d %f\t%f\n",countdown,new,new-old);
old = new;
}
if (!success) fprintf(stderr,"warning - max iterations reached\n");
return (new);
}
int
main(argc,argv)
int argc;
char **argv;
{
fastf_t *l, *x, *y, *z;
fastf_t temp0,temp1,temp2,start=0.0,end,v0,v1;
int i,j , num,plen;
fastf_t time,dist,slope,a,b,c;
plen = 0;
if (!get_args(argc,argv))
fprintf(stderr,"Usage: anim_time [-s#] [-e#] [-d] < in.table\n");
if (!domem) {
maxlines = MAXLEN;
}
l = (fastf_t *) bu_malloc(maxlines*sizeof(fastf_t),"l[]");
if (verbose) {
x = (fastf_t *) bu_malloc(maxlines*sizeof(fastf_t),"x[]");
y = (fastf_t *) bu_malloc(maxlines*sizeof(fastf_t),"y[]");
z = (fastf_t *) bu_malloc(maxlines*sizeof(fastf_t),"z[]");
} else {
x = (fastf_t *) bu_malloc(2*sizeof(fastf_t),"x[]");
y = (fastf_t *) bu_malloc(2*sizeof(fastf_t),"y[]");
z = (fastf_t *) bu_malloc(2*sizeof(fastf_t),"z[]");
}
l[0] = 0.0;
while(plen<maxlines){
i = (verbose) ? plen : plen%2;
j = (verbose) ? (plen-1) : (plen+1)%2;
num = scanf("%lf %lf %lf %lf",&end,x+i,y+i,z+i);
if (num<4)
break;
if(plen){
temp0 = x[i]-x[j];
temp1 = y[i]-y[j];
temp2 = z[i]-z[j];
l[plen] = sqrt(temp0*temp0+temp1*temp1+temp2*temp2);
l[plen] += l[plen-1];
} else {
start = end;
}
plen++;
}
time = end - start;
dist = l[plen-1];
if (query){
printf("%f\n",dist);
return(0);
}
if (time < DIVIDE_TOL){
fprintf(stderr,"anim_time: time too small. Only %f s.\n",time);
exit(-1);
}
if (dist < DIVIDE_TOL){
fprintf(stderr,"anim_time: pathlength too small. Only %f\n",dist);
exit(-1);
}
slope = dist/time;
switch (v0_set) {
case TIME_ABSOLUTE:
v0 = inv0;
break;
case TIME_RELATIVE:
v0 = slope*inv0;
break;
default:
case TIME_NONE:
v0 = slope;
break;
}
switch (v1_set) {
case TIME_ABSOLUTE:
v1 = inv1;
break;
case TIME_RELATIVE:
v1 = slope*inv1;
break;
default:
case TIME_NONE:
v1 = slope;
break;
}
if (v0<0.0) {
fprintf(stderr,"anim_time: Start velocity must be non-negative.\n");
exit(-1);
}
if (v1<0.0) {
fprintf(stderr,"anim_time: End velocity must be non-negative.\n");
exit(-1);
}
if (v0>3*slope) {
fprintf(stderr,"anim_time: Start velocity must be not be greater than %f units/s for this path.\n", 3.0*slope);
exit (-1);
}
if (v1>3*slope) {
fprintf(stderr,"anim_time: End velocity must not be greater than %f for this path.\n", 3.0*slope);
exit(-1);
}
a = ((v1+v0) - 2.0*slope)/(time*time);
b = (3*slope - (v1+2.0*v0))/time;
c = v0;
temp2 = 1.0/slope;
if (verbose) {
printf("%.12e\t%.12e\t%.12e\t%.12e\n",start,x[0],y[0],z[0]);
for (i=1; i<plen-1; i++){
temp0 = gettime(l[i],a,b,c,l[i]*temp2);
printf("%.12e\t%.12e\t%.12e\t%.12e\n",temp0+start,x[i],y[i],z[i]);
}
printf("%.12e\t%.12e\t%.12e\t%.12e\n",end,x[plen-1],y[plen-1],z[plen-1]);
} else {
printf("%.12e\n",start);
for (i=1; i<plen-1; i++){
temp0 = gettime(l[i],a,b,c,l[i]*temp2);
printf("%.12e\n",temp0+start);
}
printf("%.12e\n",end);
}
bu_free((char *) l, "l[]");
bu_free((char *) x, "x[]");
bu_free((char *) y, "y[]");
bu_free((char *) z, "z[]");
return( 0 );
}
/* code to read command line arguments*/
#define OPT_STR "ds:e:i:f:qm:v"
int get_args(argc,argv)
int argc;
char **argv;
{
int c;
while ( (c=bu_getopt(argc,argv,OPT_STR)) != EOF) {
switch(c){
case 's':
sscanf(bu_optarg,"%lf",&inv0);
v0_set = TIME_ABSOLUTE;
break;
case 'e':
sscanf(bu_optarg,"%lf",&inv1);
v1_set = TIME_ABSOLUTE;
break;
case 'i':
sscanf(bu_optarg,"%lf",&inv0);
v0_set = TIME_RELATIVE;
if ((inv0>3.0)||(inv0<0.0)) {
fprintf(stderr,"anim_time: -i argument must lie between 0.0 and 3.0\n");
exit(-1);
}
break;
case 'f':
sscanf(bu_optarg,"%lf",&inv1);
v1_set = TIME_RELATIVE;
if ((inv1>3.0)||(inv1<0.0)) {
fprintf(stderr,"anim_time: -f argument must lie between 0.0 and 3.0\n");
exit(-1);
}
break;
case 'q':
query = 1;
break;
case 'm':
sscanf(bu_optarg,"%d",&maxlines);
domem = 1;
break;
case 'v':
verbose = 1;
break;
case 'd':
debug = 1;
break;
default:
fprintf(stderr,"Unknown option: -%c\n",c);
return(0);
}
}
return(1);
}
+435
View File
@@ -0,0 +1,435 @@
.TH ANIM_TRACK 1 BRL/CAD
.SH NAME
anim_track - make an script to model or animate the pads and wheels of a
tracked vehicle.
.SH SYNOPSIS
.B
anim_track [options] wheelfile < in.table > out.script
.SH DESCRIPTION
.I anim_track
is designed to produce an animation script for the
animation of the track pads and/or the wheels which define the track.
Alternatively, track can output a file which produces a track model
when sourced by mged.
.PP
A track consists of a number of identical pads which
are wrapped in a chain around two or more ordered wheels. Normally, the
track is linear between the wheels. The exeption is that between the
first and last wheels, any extra track length is taken up in a hanging
caternary arc.
.PP
Anim_track requires two input files. The first, referred to above as
.BR wheelfile ,
is a table which
defines the initial track geometry by describing the wheels around which
the track is to be wrapped. The first three columns of the table give
the center point of the wheels, and the fourth column gives the radius
of each wheel. The table contains one line for each wheel; the
wheels should be listed in clockwise order as viewed from the right of
the vehicle. This is the direction that the track pads move around the
wheels when the vehicle is moving forward.
.PP
The track is part of a vehicle which has a front, back, left, right, up,
and down. By default these directions are +x, -x, +y, -y, +z, and -z,
respectively, but any orientation can be specified by the user with the
.B -b
option.
The track is always confined to a plane which has no left to right
variation; that is, the wheels can be in front of, behind, above, and
below each other, but may not be to the left or right of each other. If
the wheel positions specified in
.B wheelfile
do not lie in such a plane, then the first wheel defines the plane into
which all of the other wheels are projected.
.PP
The track pads are spread evenly along the entire length of the track.
The track segments between wheels are always linear, except for the
segment between the first and last wheels. If there is any extra track
length, it is taken up in a caternary arc which hangs down between the
first and last wheels. Thus if the the first wheel in
.B wheelfile
should be the top front wheel of the vehicle, and the last wheel in
.B wheelfile
should be the top back wheel of the vehicle. Depending on the track
length mode specified with the
.B -l
option, the caternary segment may or may not appear.
.PP
The second input file required by
.IR anim_track ,
referred to above as
.BR in.table ,
describes the state of the track in every frame of the animation. The
format of this second file can vary greatly according to the command-line
options. The first column of the file is ignored, but is expected to
contain the time values corresponding to each frame. Next come one or
more columns which specify directly or indirectly the distance that the
track has rolled around the wheels in each frame (see the
.BR -u ,
.BR -y ,
and
.B -s
options). Finally, the file may specify new wheel position for every
frame (see the
.B -v
option).
.PP
.SH MODEL REQUIREMENTS
Certain model conventions are needed in order for the animation to work
properly. First of all, if the wheels are to be animated, they must
all be named
.IR wheelname . i ,
where
.I i
ranges from 0 to one less than the number of wheels.
.I wheelname
is an arbitrary string.
.IR wheelname 0
must be
the top front wheel in a given track and
.IR wheelname (n-1)
must be the top
back wheel. The central axes of all the wheels should be parallel to
each other and perpendicular to a plane containing all of the wheel
centers.
.PP
The pads of the track should be identical instances or copies of a
prototype pad object, and they all should be named
.IR padname i,
where
.I i
ranges from 0 to one less than the number of pads.
The prototype pad should be centered on the origin in the x and y
directions. In the z direction, the inner, wheel-contacting surface of
the pad should lie on the z=0 plane. The outer, ground-contacting
surface should face the positive z-direction. The side of the pad which
would connect with the pad in front of it should face the positive x
direction, and the side which would connect with the pad behind it
should face the negative x direction. If the pads are a part of a higher
level combination, as they typically are, then the matrix between each
pad and the higher combination may be modified at will as long as the
prototype pad is not disturbed.
.SH OPTIONS
.TP
.B -p num_pads parent/basename
Animate the track pads. This option takes two arguments; the number of
pads in the track and a slash-separated path to the pad basename.
For
example, if there is a combination named "lpads" containing 80 track
pads with names ranging from "pad.0" to "pad.79", then the correct
arguments would be:
.sp
.B -p 79 lpads/pad.
.sp
Each frame of the output animation script will contain an animation
command for each of the track pads.
.TP
.B -w parent/basename
Animate the track wheels. This option takes one argument: a
slash-separated path to the wheel basename. The number of wheels is
obtained from the number of lines in the
.BR wheelfile .
If there is, for example, a combination named "rwheels" containing 4
wheels named wheel_0, wheel_1, wheel_2, and wheel_3, then the correct
argument is:
.sp
.B -w rwheels/wheel_
.sp
Each frame of the output animation script will contain an animation
command for each of the wheels.
.TP
.B \-b # # #
Specify the yaw, pitch, and roll of the vehicle's axes
with respect to the world axes. By default, the vehicle is assumed to
have a yaw, pitch, and roll of 0, and the track is therefore put into a
xz plane.
.TP
.B \-d # # #
Specify (in world coordinates) the centroid of the vehicle
of which the track is a part. By default, the vehicle is assumed
centered at the origin.
.TP
.B -u
User-specified track distance. The user
should provide, in the second column of
.IR in.table ,
the distance that the track should be rolled around the wheels in each
frame. This is the default.
.TP
.B -y
Derive the track distance from a table of position, yaw, pitch, and
roll. The second column through the seventh columns of the
.I in.table
should contain the position and orientation of the vehicle in every
frame. The distance that the track should be rolled around the wheels is
automatically calculated in every frame. If
.I anim_script
is being used with the same table to create the animaion script for the
vehicle itself, the
.B -b
and
.B -d
options to
.I anim_script
and
.I anim_track
should be the same.
.TP
.B -s
Derive the track distance from a table of positions, using automatic
steering. The second column through the fourth column of the
.I in.table
should contain the position of the vehicle in every frame. The distance
that the track should be rolled around the wheels is automatically
calculated in every frame, based on the assumption that the vehicle is
always steered to face the direction of motion.
If
.I anim_script
is being used with the same table to create the animaion script for the
vehicle itself, the
.B -b
and
.B -d
options to
.I anim_script
and
.I anim_track
should be the same.
.TP
.B -a
Enable anti-strobing measures. When the track is rolling fast enough, track
animations exhibit a strobing effect which may make the track appear to
slow down or rotate backwards. This is an artifact of the discrete time
nature of the animations, and occurs when the distance traveled by the
track in one frame is close to the pad length. If the
.B -a
option is selected,
.I anim_track
adds random jitter to the track's motion when the track speed is high
enough to cause strobing. This causes a motion blur effect rather than
strobing.
.TP
.B -v
Specify new wheel positions in every frame. This option allows dynamic
suspensions to be animated. If there are n wheels, then the last 2n
columns of
.I in.table
should contain the front-back and up-down coordinates of each wheel,
relative to the vehicle center and orientation specified with
.B -d
and
.BR -b .
The columns should be in pairs: The front-back coordinate of the first
wheel, followed by its up-down coordinate, followed by the front-back
coordinate of the second wheel, and so on.
.sp
If this option is not specified, then the wheel positions are fixed
throughout the animation.
.TP
.B -c
Calculate the track circumference, that is, the length of the shortest
track that can wrap around a given set of wheels. If the -v option is
specified, then
the output is a table containing the frame number and the track
circumference in each frame. Otherwise, a single value representing the
constant track circumference is returned.
.TP
.B -lm
Minimize the track length. With this option the length of the track is
set to the track circumference in every frame, ie the track shrinks to
fit the wheels.
.TP
.B -lf #
Specify a fixed track length. The argument specifies the track length, which
remains constant throughout the animation. If at any time the track
circumference exceeds the track length, the program is aborted and a
message is printed on standard error.
.TP
.B -ls #
Specify a stretchable track. The argument specifies the initial track
length. If at any time the track circumference exceeds the track length,
the track length is increased to meet the need. The track length never
decreases once it has been increased.
.TP
.B -le #
Specify an elastic track. The argument specifies the initial track
length. If at any time the track circumference exceeds the track length,
the track length is increased to meet the need. When the track
circumference decreases again, the track length also decreases, but it
never gets shorter than its original length.
.TP
.B -i #
Specify the initial offset of the track. By default, the first track pad
is initially placed at the point where the caternary arc meets the first
wheel. If an offset is specified, it represents the distance clockwise
around the track to from this point to the desired initiall point of
the first pad. This option is typically used to align the track pads
with drive wheel teeth.
.TP
.B -f #
Specify the integer with which to begin numbering the frames of the
animation script. The default is zero.
.TP
.B -r #
Specify the common radius of all the wheels. In this case, the fourth column
should be omitted from the
.BR wheelfile .
.TP
.B -g #
Instead of an animation script, create a file which can be sourced by
.I mged
to edit the track geometry. This will actually wrap the modeled pad
instances around the wheels.
The argument is the number of the frame which is to be emulated. For
example, to model the pads in the positions they will have in the first
frame of an animation, the specified frame number would be zero.
.TP
.B -mp command
Specify the animation matrix command to apply to the pads. The default
value is "rarc", meaning that the matrix between the pad and its parent
is replaced by a new matrix. See the
.I anim_script
man page for more information.
.TP
.B -mw command
Specify the animation matrix command to apply to the wheels. The default
value is "lmul", meaning that the new matrix is multiplied onto the left
of the old matrix between the pad and its parent combination. See the
.I anim_script
man page for more information.
.SH EXAMPLES
A typical use of
.I anim_track
would be to make an animation of a tank rolling across
bumpy ground. By some method (such as physical simulation)
you obtain the position of the center of
the tank and its orientation at each time. You also nead to obtain the
position of the each wheel relative to the vehicle center at each time.
All of this information is placed in
.BR in.table .
The model of the tank is stored in
model.g as a combination named "tank". Its centroid is at the
point (0,0,1005) and it faces the y-axis. An animation script for the
tank itself is created as follows:
.PP
anim_script -d 0 0 1005 -b 90 0 0 /tank < tank.table > tank.script
.PP
Here
.B tank.table
specifies the position and orientation of the tank in each frame; the
.B \-d
and
.B \-b
options specify the original position and orientation of the tank in the
database.
.PP
To create the model of the track, a prototype track pad is created,
centered on the origin in the x and y directions, with the
wheel-contacting surface face-down on the origin. The pad is 100mm
long and 5mm thick. Ninety-six instances of the pad are created, with names "rpad.0"
through "rpad.95", and grouped together in a combination called "rtrack".
.PP
Now, a file called
.B rwheelfile
is created, describing the positions and radii of the four wheels in the
right track:
.nf
1300 2000 1005 60
1300 1500 55 50
1300 -1500 55 50
1300 -2000 1005 60
.fi
Two roadwheels both have radius 50mm, while the idler and drivewheels
have a 60mm radius, and the wheels are named wh.0, wh.1, wh.2, and wh.3.
.PP
The following call checks the circumference of the track:
.nf
%> anim_track -c rwheelfile
9502.448956
.fi
The 96 100mm-long pads should be sufficient to wrap around the wheels,
leaving a shallow caternary arc between the idler and driver wheels.
.PP
The following call creates a file which can be used by
.I mged
to wrap the pads around the wheels in the model.
.nf
%> anim_track -g 0 -b 90 0 0 -d 0 0 100 -lf 9600 -p 96 rtrack/rpad.
rwheelfile <<EOF > rtrack.src
? 0 0
? EOF
.fi
In this case,
.I in.table
consisted of only one row and two columns. The two columns represented
time and the distance the track should be rolled from it's initial
position. The
.B -g
option was set to 0 since frame zero was the only frame in the
input table.
The changes are applied to the geometry in
.I mged
with the following command:
.nf
mged> source rtrack.src
.fi
The pads are now permanently modeled in their new positions.
.PP
In order to animate the pads and wheels, the following command would be
appropriate:
.PP
anim_track -p 96 rtrack/rpad. -w rwheel/wh. -d 0 0 1005 -b 90 0 0 -y -v -lf
9600 rwheelfile < in.table > rtrack.script
.PP
The in.table contains 15 columns specifying the time, the 3D position and
yaw, pitch, and roll of the vehicle, and the front-back and up-down
coordinates of each of the four wheels relative to the vehicle center.
For example, one row of
.B in.table
could be:
.PP
0.5 234.0 1415.6 1005 45 0 0 2000 0 1500 -950 -1500 -950 -2000 -10
.PP
This would specify the new position of the vehicle half of a second into
the animation, and indicate that
the first three wheels remained in their original positions
while the fourth wheel had dropped 10mm.
Note that the previous step (modeling) wasn't necessary in order for the
animation to work.
.PP
.B rtrack.script
by itself causes the wheels to move and rotate and the
pads to roll around them. When the entire tank, including to track,
is moved along across the ground by
.BR track.script ,
the full effect is acheived. The two scripts
could be combined
with a script for the left track, using
.IR script_sort ,
to make the complete script.
.PP
.SH BUGS
Tracks must have at least two wheels. The front edge of wheel.(n-1) must
stay behind the back edge of wheel.0, or the results are unpredictable.
(Usually a lot of NaN's on the output).
.SH SEE ALSO
anim_script(1)
.SH AUTHOR
Carl J. Nuzman
.SH COPYRIGHT
This software is Copyright (C) 1996-2004 by the United States Army
in all countries except the USA. All rights reserved.
.SH "BUG REPORTS"
Reports of bugs or problems should be submitted via electronic
mail to <CAD@ARL.ARMY.MIL>.
+694
View File
@@ -0,0 +1,694 @@
/* A N I M _ T R A C K . C
*
* Animate the links and wheels of a tracked vehicle. Handles tracks that
* change in shape during the animation.
*
* Author -
* Carl J. Nuzman
*
* Source -
* The U. S. Army Research Laboratory
* Aberdeen Proving Ground, Maryland 21005-5068 USA
*
* Distribution Notice -
* Re-distribution of this software is restricted, as described in
* your "Statement of Terms and Conditions for the Release of
* The BRL-CAD Pacakge" agreement.
*
* Copyright Notice -
* This software is Copyright (C) 1993-2004 by the United States Army
* in all countries except the USA. All rights reserved.
*/
#include "conf.h"
#ifdef USE_STRING_H
#include <string.h>
#else
#include <strings.h>
#endif
#include <math.h>
#include <stdio.h>
#include "machine.h"
#include "externs.h"
#include "vmath.h"
#include "raytrace.h"
#include "anim.h"
#ifndef M_PI
#define M_PI 3.14159265358979323846
#endif
#ifndef M_PI_2
#define M_PI_2 1.57079632679489661923
#endif
#define GIVEN 0
#define CALCULATED 1
#define STEERED 2
#define PRINT_ANIM 0
#define PRINT_ARCED 1
#define TRACK_MIN 0
#define TRACK_FIXED 1
#define TRACK_STRETCH 2
#define TRACK_ELASTIC 3
#define NW num_wheels
#define NEXT(i) (i+1)%NW
#define PREV(i) (i+NW-1)%NW
typedef double *pdouble;
struct wheel {
vect_t pos; /* displacement of wheel from vehicle origin */
fastf_t rad; /* radius of wheel */
fastf_t ang0; /* angle where track meets wheel 0<a<2pi*/
fastf_t ang1; /* angle where track leaves wheel 0<a<p2i */
fastf_t arc; /* radian length of contact between wheel and track 0<a<pi*/
};
struct track {
vect_t pos0; /* beginning point of track section */
vect_t pos1; /* end of track section */
vect_t dir; /* unit vector:direction of track section ending here*/
fastf_t len; /* length of track section ending here*/
};
struct slope {
vect_t dir; /* vector from previous to current axle*/
fastf_t len; /* length of vector above*/
};
struct all {
struct wheel w; /* parameters describing the track around a wheel */
struct track t; /* track between this wheel and the previous wheel */
struct slope s; /* vector between this axle and the previous axle */
};
/* external variables */
extern int bu_optind;
extern char *bu_optarg;
/* variables describing track geometry - used by main, trackprep, get_link*/
struct all *x;
fastf_t curve_a, curve_b, curve_c, s_start;
int num_links, num_wheels;
fastf_t track_y, tracklen, first_tracklen;
/* variables set by get_args */
int wheel_nindex; /* argv[wheel_nindex] = wheelname*/
int link_nindex; /* argv[link_nindex] = linkname*/
int print_wheel; /* flag: do wheel animation */
int print_link; /* flag: do link animation */
int print_mode; /* anim for rt or arced for mged */
int arced_frame; /* which frame to arced */
int axes, cent; /* flags: alternate axes, centroid specified */
int dist_mode; /* given, steered, or calculated */
int first_frame; /* integer to begin numbering frames */
fastf_t init_dist; /* initial distance of first link along track */
int one_radius; /* flag: common radius specified */
fastf_t radius; /* common radius of all wheels */
vect_t centroid, rcentroid; /* alternate centroid and its reverse */
mat_t m_axes, m_rev_axes; /* matrices to and from alternate axes */
char link_cmd[10]; /* default is "rarc" */
char wheel_cmd[10]; /* default is "lmul" */
int get_circumf; /* flag: just return circumference of track */
int read_wheels; /* flag: read new wheel positions each frame */
int len_mode; /* mode for track_len */
int anti_strobe; /* flag: take measures against strobing effect */
int
main(argc,argv)
int argc;
char **argv;
{
void anim_y_p_r2mat(), anim_add_trans(), anim_mat_print();
int get_args(), get_link(), track_prep(), val, frame, i, count;
int go;
fastf_t y_rot, distance, yaw, pch, roll;
vect_t cent_pos, wheel_now, wheel_prev;
vect_t zero, position, vdelta, temp, to_track, to_front;
mat_t wmat, mat_x;
FILE *stream;
struct wheel *wh;
int last_steer, last_frame;
int rndtabi=0;
fastf_t halfpadlen, delta, prev_dist;
VSETALL(zero,0.0);
VSETALL(to_track,0.0);
VSETALL(centroid,0.0);
VSETALL(rcentroid,0.0);
y_rot = 0.0;
num_wheels = 0;
last_steer = last_frame = 0;
MAT_IDN(mat_x);
MAT_IDN(wmat);
MAT_IDN(m_axes);
MAT_IDN(m_rev_axes);
if (!get_args(argc,argv))
fprintf(stderr,"Anim_track: Argument error.\n");
if (axes || cent ){ /* vehicle has own reference frame */
anim_add_trans(m_axes,centroid,zero);
anim_add_trans(m_rev_axes,zero,rcentroid);
}
/* get track information from specified file */
if (!(stream = fopen(*(argv+bu_optind),"r"))){
fprintf(stderr,"Track: Could not open file %s.\n",*(argv+bu_optind));
return(0);
}
num_wheels = -1;
if (one_radius) {
while (!feof(stream)) {
fscanf(stream,"%*f %*f %*f");
num_wheels++;
}
} else {
while (!feof(stream)) {
fscanf(stream,"%*f %*f %*f %*f");
num_wheels++;
}
}
rewind(stream);
/*allocate memory for track information*/
/* x: contains track geometry for the current frame */
x = (struct all *) calloc(num_wheels,sizeof(struct all));
/* wh: contains geometry of wheels in mged database */
wh = (struct wheel *) calloc(num_wheels,sizeof(struct wheel));
/*read original wheel positions*/
for (i=0;i<NW;i++){
fscanf(stream,"%lf %lf %lf", temp, temp+1, temp+2);
if (one_radius)
x[i].w.rad = radius;
else
fscanf(stream,"%lf",& x[i].w.rad);
MAT4X3PNT(x[i].w.pos,m_rev_axes,temp);
if (i==0)
track_y = x[0].w.pos[1];
else
x[i].w.pos[1] = track_y;
wh[i].pos[0] = x[i].w.pos[0];
wh[i].pos[1] = x[i].w.pos[1];
wh[i].pos[2] = x[i].w.pos[2];
wh[i].rad = x[i].w.rad;
}
(void) fclose(stream);
/* initialize to_track */
VSET(to_track, 0.0, track_y, 0.0);
VSET(to_front,1.0,0.0,0.0);
if (get_circumf&& (!read_wheels)) {
track_prep();
printf("%.10g\n",tracklen);
return(0);
}
if (dist_mode==STEERED) {
/* prime the pumps */
scanf("%*f");/*time*/
val = scanf("%lf %lf %lf", cent_pos, cent_pos+1, cent_pos + 2);
if (val < 3)
return(0);
go = anim_steer_mat(mat_x, cent_pos, 0);
last_steer = 0;
} else {
go = 1;
}
if (anti_strobe) {
BN_RANDSEED(rndtabi, 0);
}
/* main loop */
prev_dist = distance = 0.0;
frame = first_frame;
for ( ; ; frame++) {
if (dist_mode==GIVEN){
scanf("%*f");/*time*/
val = scanf("%lf",&distance);
if (val < 1) {
break;
}
}
else if (dist_mode==CALCULATED){
scanf("%*f");/*time*/
scanf("%lf %lf %lf", cent_pos, cent_pos+1, cent_pos+2);
val = scanf("%lf %lf %lf",&yaw,&pch,&roll);
if (val < 3)
break;
anim_dy_p_r2mat(mat_x,yaw,pch,roll);
anim_dy_p_r2mat(mat_x,yaw,pch,roll);
anim_add_trans(mat_x,cent_pos,rcentroid);
}
if (read_wheels) {
/* read in all wheel positions */
for(i=0;i<NW;i++){
val=scanf("%lf %lf",x[i].w.pos, x[i].w.pos + 2);
if (val < 2) {
break;
}
}
}
if (dist_mode==STEERED) {
scanf("%*f");/*time*/
val = scanf("%lf %lf %lf", cent_pos, cent_pos+1, cent_pos + 2);
if (val < 3){
if (last_steer)
break;
else
last_steer = 1;
}
go = anim_steer_mat(mat_x, cent_pos, last_steer);
anim_add_trans(mat_x,cent_pos,rcentroid);
}
/* call track_prep to calculate geometry of track */
if ((frame==first_frame)||read_wheels) {
if ((track_prep())==-1){
fprintf(stderr,"Track: error in frame %d: track too short.\n",frame);
break;
}
if (get_circumf) {
printf("%d\t%.10g\n",frame,tracklen);
}
}
if ((dist_mode==CALCULATED)||(dist_mode==STEERED)){
/*determine distance traveled*/
VMOVE(wheel_prev,wheel_now);
MAT4X3PNT(wheel_now,mat_x,to_track);
if (frame > first_frame){ /* increment distance by distance moved*/
VSUB2(vdelta,wheel_now,wheel_prev);
MAT3X3VEC(temp,mat_x,to_front);/*new front of vehicle*/
distance += VDOT(temp,vdelta);/*portion of vdelta in line with track*/
}
}
if (anti_strobe) {
halfpadlen = 0.5 * tracklen/(fastf_t) num_links;
delta = distance - prev_dist;
prev_dist = distance;
if ((delta >= halfpadlen)||(delta <= -halfpadlen)) {
distance += BN_RANDOM(rndtabi) * 2.0* halfpadlen;
}
}
if (go && (!get_circumf)) {
if (print_mode==PRINT_ANIM) {
printf("start %d;\nclean;\n", frame);
} else if (print_mode==PRINT_ARCED) {
if (frame != arced_frame) continue;
last_frame = 1;
}
if (print_link) {
for (count=0;count<num_links;count++){
(void) get_link(position,&y_rot,distance+tracklen*count/num_links+init_dist);
anim_y_p_r2mat(wmat,0.0,y_rot,0.0);
anim_add_trans(wmat,position,zero);
if (axes || cent){ /* link moved to vehicle coords */
MAT_MOVE(mat_x,wmat);
bn_mat_mul(wmat,m_axes,mat_x);
}
if (print_mode==PRINT_ANIM) {
printf("anim %s%d matrix %s\n", *(argv+link_nindex),count,link_cmd);
anim_mat_printf(stdout,wmat,"%.10g ","\n",";\n");
} else if (print_mode==PRINT_ARCED) {
printf("arced %s%d matrix %s ", *(argv+link_nindex),count,link_cmd);
anim_mat_printf(stdout,wmat,"%.10g ","","\n");
}
}
}
if (print_wheel){
for (count = 0;count<num_wheels;count++){
anim_y_p_r2mat(wmat,0.0,-distance/wh[count].rad,0.0);
VREVERSE(temp,wh[count].pos);
anim_add_trans(wmat,x[count].w.pos,temp);
if (axes || cent){
bn_mat_mul(mat_x,wmat,m_rev_axes);
bn_mat_mul(wmat,m_axes,mat_x);
}
if (print_mode==PRINT_ANIM) {
printf("anim %s%d matrix %s\n",*(argv+wheel_nindex),count,wheel_cmd);
anim_mat_printf(stdout,wmat,"%.10g ","\n",";\n");
} else if (print_mode==PRINT_ARCED) {
printf("arced %s%d matrix %s ",*(argv+wheel_nindex),count,wheel_cmd);
anim_mat_printf(stdout,wmat,"%.10g ","","\n");
}
}
}
if (print_mode==PRINT_ANIM)
printf("end;\n");
}
if (last_frame) break;
}
free(x);
free(wh);
return( 0 );
}
#define OPT_STR "sycuvb:d:f:i:r:p:w:g:m:l:a"
int get_args(argc,argv)
int argc;
char **argv;
{
int c, i;
fastf_t yaw, pch, rll;
void anim_dx_y_z2mat(), anim_dz_y_x2mat();
/* defaults*/
wheel_nindex = link_nindex = 0;
axes = cent = print_wheel = print_link = 0;
arced_frame = first_frame = 0;
init_dist = radius = 0.0;
one_radius = get_circumf = read_wheels = 0;
strcpy(link_cmd, "rarc");
strcpy(wheel_cmd, "lmul");
print_mode = PRINT_ANIM;
dist_mode = GIVEN;
len_mode = TRACK_MIN;
anti_strobe = 0;
while ( (c=bu_getopt(argc,argv,OPT_STR)) != EOF) {
i=0;
switch(c){
case 's':
dist_mode = STEERED;
break;
case 'y':
dist_mode = CALCULATED;
break;
case 'c':
get_circumf = 1;
break;
case 'u':
dist_mode = GIVEN;
break;
case 'v':
read_wheels = 1;
break;
case 'b':
bu_optind -= 1;
sscanf(argv[bu_optind+(i++)],"%lf", &yaw );
sscanf(argv[bu_optind+(i++)],"%lf", &pch );
sscanf(argv[bu_optind+(i++)],"%lf", &rll );
bu_optind += 3;
anim_dx_y_z2mat(m_axes, rll, -pch, yaw);
anim_dz_y_x2mat(m_rev_axes, -rll, pch, -yaw);
axes = 1;
break;
case 'd':
bu_optind -= 1;
sscanf(argv[bu_optind+(i++)],"%lf",centroid);
sscanf(argv[bu_optind+(i++)],"%lf",centroid+1);
sscanf(argv[bu_optind+(i++)],"%lf",centroid+2);
bu_optind += 3;
VREVERSE(rcentroid,centroid);
cent = 1;
break;
case 'f':
sscanf(bu_optarg,"%d",&first_frame);
break;
case 'i':
sscanf(bu_optarg,"%lf",&init_dist);
break;
case 'r':
sscanf(bu_optarg,"%lf",&radius);
one_radius = 1;
break;
case 'p':
sscanf(bu_optarg,"%d", &num_links);
link_nindex = bu_optind;
bu_optind += 1;
print_link = 1;
break;
case 'w':
wheel_nindex = bu_optind - 1;
/*sscanf(bu_optarg,"%s",wheel_name);*/
print_wheel = 1;
break;
case 'g':
sscanf(bu_optarg,"%d",&arced_frame);
print_mode = PRINT_ARCED;
break;
case 'm':
switch (*bu_optarg) {
case 'p':
strncpy(link_cmd,argv[bu_optind], 10);
break;
case 'w':
strncpy(wheel_cmd,argv[bu_optind], 10);
break;
default:
fprintf(stderr,"Unknown option: -m%c\n",*bu_optarg);
return(0);
}
bu_optind += 1;
break;
case 'l':
switch (*bu_optarg) {
case 'm':
len_mode = TRACK_MIN;
break;
case 'f':
len_mode = TRACK_FIXED;
sscanf(argv[bu_optind],"%lf",&first_tracklen);
tracklen = first_tracklen;
bu_optind++;
break;
case 's':
len_mode = TRACK_STRETCH;
sscanf(argv[bu_optind],"%lf",&first_tracklen);
tracklen = first_tracklen;
bu_optind++;
break;
case 'e':
len_mode = TRACK_ELASTIC;
sscanf(argv[bu_optind],"%lf",&first_tracklen);
tracklen = first_tracklen;
bu_optind++;
break;
default:
fprintf(stderr,"Unknown option: -l%c\n",*bu_optarg);
return(0);
}
break;
case 'a':
anti_strobe = 1;
break;
default:
fprintf(stderr,"Unknown option: -%c\n",c);
return(0);
}
}
return(1);
}
/* TRACK_PREP - Calculate the geometry of the track. Wheel positions and
* radii should already exist in the x[i] structs. Track_prep fills in the
* rest of the x[i] structs and also calculates values for curve_a, curve_b,
* curve_c, and s_start, which describe the caternary segment
* return values: 0 = GOOD
* -1 = BAD. Track too short to fit around wheels
*/
int track_prep()
{
int i;
fastf_t phi, costheta, arc_angle;
fastf_t linearlen, hyperlen;
vect_t difference;
int getcurve();
fastf_t hyper_get_s();
/* first loop - get inter axle slopes and start/end angles */
for (i=0;i<NW;i++){
/*calculate current slope vector*/
VSUB2(x[i].s.dir,x[i].w.pos,x[PREV(i)].w.pos);
x[i].s.len = MAGNITUDE(x[i].s.dir);
/*calculate end angle of previous wheel assuming all convex*/
phi = atan2(x[i].s.dir[2],x[i].s.dir[0]);/*absolute angle of slope*/
costheta = (x[PREV(i)].w.rad - x[i].w.rad)/x[i].s.len;/*cosine of special angle*/
x[PREV(i)].w.ang1 = phi + acos(costheta);
while (x[PREV(i)].w.ang1 < 0.0)
x[PREV(i)].w.ang1 += 2.0*M_PI;
x[i].w.ang0 = x[PREV(i)].w.ang1;
}
/* second loop - handle concavities */
for (i=0;i<NW;i++){
arc_angle = x[i].w.ang0 - x[i].w.ang1;
while (arc_angle < 0.0)
arc_angle += 2.0*M_PI;
if (arc_angle > M_PI) { /* concave */
x[i].w.ang0 = 0.5*(x[i].w.ang0 + x[i].w.ang1);
x[i].w.ang1 = x[i].w.ang0;
x[i].w.arc = 0.0;
}
else { /* convex - angles are already correct */
x[i].w.arc = arc_angle;
}
}
/* third loop - calculate geometry of straight track segments */
for (i=0;i<NW;i++){
/*calculate endpoints of track segment*/
x[i].t.pos1[0] = x[i].w.pos[0] + x[i].w.rad*cos(x[i].w.ang0);
x[i].t.pos1[1] = x[i].w.pos[1];
x[i].t.pos1[2] = x[i].w.pos[2] + x[i].w.rad*sin(x[i].w.ang0);
x[i].t.pos0[0] = x[PREV(i)].w.pos[0] + x[PREV(i)].w.rad*cos(x[PREV(i)].w.ang1);
x[i].t.pos0[1] = x[PREV(i)].w.pos[1];
x[i].t.pos0[2] = x[PREV(i)].w.pos[2] + x[PREV(i)].w.rad*sin(x[PREV(i)].w.ang1);
/*calculate length and direction of track segment*/
VSUB2(difference,x[i].t.pos1,x[i].t.pos0);
x[i].t.len = MAGNITUDE(difference);
VSCALE((x[i].t.dir),difference,(1.0/x[i].t.len));
}
/* calculate total track length used so far*/
linearlen = x[0].w.arc*x[0].w.rad;
for (i=1;i<NW;i++){
linearlen += x[i].t.len;
linearlen += x[i].w.arc*x[i].w.rad;
}
if (len_mode==TRACK_MIN) {
tracklen = linearlen + x[0].t.len;
curve_a = 0.0;
return(0); /* early return */
}
if (len_mode==TRACK_ELASTIC) {
tracklen = first_tracklen;
}
/* calculate geometry of hyperbolic segment */
hyperlen = tracklen - linearlen;
if(hyperlen < x[0].t.len){ /* desired length of hyperbola less than straight line*/
if((len_mode==TRACK_ELASTIC)||(len_mode==TRACK_STRETCH)){
tracklen += (x[0].t.len-hyperlen);
hyperlen = tracklen - linearlen;
}
else{
return(-1);/*bad, track is too short*/
}
}
getcurve(&curve_a,&curve_b,&curve_c,&(x[NW-1].w.ang1),&(x[0].w.ang0),hyperlen,x[NW-1].w.pos,x[0].w.pos,x[NW-1].w.rad,x[0].w.rad);
/* re-evaluate zeroth track section in light of curve information */
x[0].t.pos0[X] = x[NW-1].w.pos[X] + x[NW-1].w.rad * cos(x[NW-1].w.ang1);
x[0].t.pos0[Z] = x[NW-1].w.pos[Z] + x[NW-1].w.rad * sin(x[NW-1].w.ang1);
x[0].t.pos1[X] = x[0].w.pos[X] + x[0].w.rad * cos(x[0].w.ang0);
x[0].t.pos1[Z] = x[0].w.pos[Z] + x[0].w.rad * sin(x[0].w.ang0);
VSUB2(difference,x[0].t.pos1,x[0].t.pos0);
x[0].t.len = MAGNITUDE(difference);
VSCALE(x[0].t.dir,difference,(1.0/x[0].t.len));
if (curve_a > VDIVIDE_TOL)
s_start = hyper_get_s(curve_a, 0.0, x[0].t.pos0[X] - curve_c);
x[0].w.arc = x[0].w.ang0 - x[0].w.ang1;
if (x[0].w.arc<0.0)
x[0].w.arc += 2.0*M_PI;
x[NW-1].w.arc = x[NW-1].w.ang0 - x[NW-1].w.ang1;
if (x[NW-1].w.arc<0.0)
x[NW-1].w.arc += 2.0*M_PI;
return(0); /*good*/
}
/* GET_LINK - Find the position and angle of a link which is a given
* distance around the track, measured from the point where the caternary
* section meets wheel.0.
*/
int get_link(pos,angle_p,dist)
fastf_t *angle_p, dist;
vect_t pos;
{
int i;
vect_t temp;
fastf_t hyper_get_x(), hyper_get_z(), hyper_get_ang();
while (dist >= tracklen) /*periodicize*/
dist -= tracklen;
while (dist < 0.0)
dist += tracklen;
/* we want it to ignore the distance between wheel(n-1) and wheel(0)*/
dist += x[0].t.len;
for (i=0;i<NW;i++){
if ( (dist -= x[i].t.len) < 0 ){
VSCALE(temp,(x[i].t.dir),dist);
VADD2(pos,x[i].t.pos1,temp);
*angle_p = atan2(x[i].t.dir[2],x[i].t.dir[0]);
return(2*i);
}
if ((dist -= x[i].w.rad*x[i].w.arc) < 0){
*angle_p = dist/x[i].w.rad;
*angle_p = x[i].w.ang1 - *angle_p;/*from x-axis to link*/
pos[X] = x[i].w.pos[X] + x[i].w.rad*cos(*angle_p);
pos[Y] = x[i].w.pos[Y];
pos[Z] = x[i].w.pos[Z] + x[i].w.rad*sin(*angle_p);
*angle_p -= M_PI_2; /*angle of clockwise tangent to circle*/
return(2*i+1);
}
}
/* caternary section */
if ( curve_a > VDIVIDE_TOL){
pos[X] = hyper_get_x(curve_a, 0.0, s_start+dist);
pos[Y] = x[0].w.pos[Y];
pos[Z] = hyper_get_z(curve_a,curve_b,0.0, pos[X]);
pos[X] += curve_c;
*angle_p = hyper_get_ang(curve_a,curve_c, pos[X]);
}
else { /* practically linear */
VSCALE(temp,(x[0].t.dir),dist);
VADD2(pos,x[0].t.pos0,temp);
*angle_p = atan2(x[0].t.dir[Z],x[0].t.dir[X]);
}
return -1;
}
void show_info(which)/* for debugging - -1:track 0:both 1:link*/
int which;
{
int i;
if (which <=0){
fprintf(stderr,"track length: %f\n",tracklen);
fprintf(stderr,"link length: %f\n",tracklen/num_links);
for (i=0;i<NW;i++){
fprintf(stderr,"wheel %d: \n",i);
fprintf(stderr," pos\t%f\t%f\t%f\t\n",x[i].w.pos[X],x[i].w.pos[Y],x[i].w.pos[Z]);
fprintf(stderr," rad\t%f\tang0\t%f\tang1\t%f\tarc\t%f\n",x[i].w.rad,x[i].w.ang0,x[i].w.ang1,x[i].w.arc);
fprintf(stderr,"track %d: \n",i);
fprintf(stderr," pos0\t%f\t%f\tpos1\t%f\t%f\n",x[i].t.pos0[X],x[i].t.pos0[Z],x[i].t.pos1[X],x[i].t.pos1[Z]);
fprintf(stderr," dir\t%f\t%f\t%f\tlen\t%f\n",x[i].t.dir[X],x[i].t.dir[Y],x[i].t.dir[Z],x[i].t.len);
fprintf(stderr,"slope %d: %f %f %f %f\n",i,x[i].s.dir[0],x[i].s.dir[1],x[i].s.dir[2],x[i].s.len);
}
}
/* if (which >= 0){
fprintf(stderr,"%d %f %f %f %f\n",count,position[0],position[1],position[2],y_rot);
}*/
}
+95
View File
@@ -0,0 +1,95 @@
.TH ANIM_TURN 1 BRL/CAD
.SH NAME
anim_turn - make animation table for vehicle with front-wheel steering.
.SH SYNOPSIS
.B anim_turn -l length
.B [-a angle]
.B [-r radius]
.B [-f factor]
.B [-p integer]
.B < in.table
.B > out.table
.SH DESCRIPTION
The motion of a front wheel steered vehicle is not simple - the
instaneous velocity of the front wheels is in the direction they are
pointed, while the instantaneous velocity of the back wheels is the
direction the vehicle is pointed. The purpose of
.I anim_turn
is to
produce a complete animation table for such a vehicle, given a table
specifying the desired position of the front axle at each relevant
time step. The input table should contain four columns, specifying the
time and 3D position of the center of the front axle. Actually, the path
is assumed to be confined to an x-y plane, but the three columns are
included for consistency with other animation routines.
.PP
The output is normally a seven-column table which is a copy of
the input table with three extra columns specifying the yaw,
pitch, and roll of the truck at each time. The pitch and roll
are always zero, since the motion is assumed be in an x-y plane.
.PP
The
.B \-l#
option is not optional, and is used to specify the length
of the wheelbase (from the front axle to the rear axle).
.PP
.SH OPTIONS
.TP
.B \-a#
.I Track
assumes that the truck should initially be oriented
along the line defined by the first two positions in the input table.
Otherwise, the desired initial yaw of the truck can be specified with the
.B \-a#
option.
.TP
.B \-r#
Specify the radii of the front wheels. If this option is selected,
.I track
will create an animation script to animate the front wheels. The output
table would contain four columns: time, swivel-angle, roll, and a zero
channel. These represent the orientation of the front wheels, in terms
of yaw, pitch, and roll, and the table can be piped directly to
.IR anim_script .
.TP
.B \-f#
Specify a factor to be used to animate a steering wheel. If this option
is selected, the output table will contain four columns: time, swivel,
and two zero columns. This table can be used directly by
.I anim_script
to make an animation script for a steering wheel. The argument to the
option should be the factor by which to exagerate the swiveling of
the wheels. For
example, on a typical truck, you may need to turn the steering wheel 360
degrees in order for the wheels to swivel 20 degrees. To model this
effect, a factor of 18 would be used.
.TP
.B \-p#
Specify the ratio of input rows to output rows,
which must be an integer. The default, of course, is one. The accuracy
of the output depends on having a large number of input lines, which is
not usually a problem in animations, which require a large number of
frames per second. However, if a test animation with a small number of
frames per second is being created, the user should give an input table
with a high number of input rows and reduce the output with the
.B \-p#
option. For example, if
.B in.table
contains 30 rows for each second of the
animation, then the command
.sp
.B
anim_turn -l 3000 -p10 < in.table > out.table
.sp
would produce an animation table containing 3 rows for each second of
the animation.
.SH BUGS
The algorithm used only works for motion in an x-y plane.
.SH AUTHOR
Carl J. Nuzman
.SH COPYRIGHT
This software is Copyright (C) 1993-2004 by the United States Army
in all countries except the USA. All rights reserved.
.SH "BUG REPORTS"
Reports of bugs or problems should be submitted via electronic
mail to <CAD@ARL.ARMY.MIL>.
+185
View File
@@ -0,0 +1,185 @@
/* A N I M _ T U R N . C
*
* Animate front-wheel steered vehicles.
*
* This is a filter which operates on animation tables. Given an
* animation table for the position of the front axle, anim_turn produces
* an animation table for position and orientation. Options provide for
* animating the wheels and/or steering wheel.
*
* Author -
* Carl J. Nuzman
*
* Source -
* The U. S. Army Research Laboratory
* Aberdeen Proving Ground, Maryland 21005-5068 USA
*
* Distribution Notice -
* Re-distribution of this software is restricted, as described in
* your "Statement of Terms and Conditions for the Release of
* The BRL-CAD Pacakge" agreement.
*
* Copyright Notice -
* This software is Copyright (C) 1993-2004 by the United States Army
* in all countries except the USA. All rights reserved.
*/
#include "conf.h"
#include <math.h>
#include <stdio.h>
#include "machine.h"
#include "vmath.h"
#include "bu.h"
#include "anim.h"
#ifndef M_PI
#define M_PI 3.14159265358979323846
#endif
int get_args();
extern void anim_y_p_r2mat();
extern void anim_add_trans();
extern int bu_optind;
extern char *bu_optarg;
int print_int = 1;
int angle_set = 0;
int turn_wheels = 0;
fastf_t length, angle, radius;
fastf_t factor = 1.0;
int
main(argc,argv)
int argc;
char **argv;
{
int count;
fastf_t val, time, roll_ang, yaw,sign;
vect_t v, point, front, back, zero, temp1, temp2;
mat_t m_from_world, m_to_world;
double bn_atan2();
/* initialize variables */
VSETALL(zero, 0.0);
VSETALL( v , 0.0 );
VSETALL( point, 0.0 );
VSETALL( front, 0.0 );
VSETALL( back, 0.0 );
VSETALL( temp1, 0.0 );
VSETALL( temp2, 0.0 );
for( count=0 ; count<ELEMENTS_PER_MAT ; count++ )
m_from_world[count]=m_to_world[count]=0.0;
length = angle = radius = roll_ang = 0.0;
if (!get_args(argc,argv))
fprintf(stderr,"ascript: Get_args error");
if (!angle_set) { /* set angle if not yet done */
scanf("%*f%*[^-0123456789]");
VSCAN(temp1);
scanf("%*f%*[^-0123456789]");
VSCAN(temp2);
angle = bn_atan2( (temp2[1]-temp1[1]),(temp2[0]-temp1[0]) );
rewind(stdin);
}
count = 0;
while (1) {
/* read one line of table */
val = scanf("%lf%*[^-0123456789]",&time); /*read time,ignore garbage*/
val = scanf("%lf %lf %lf", point, point+1, point +2);
if (val < 3) {
break;
}
/*update to and from matrices */
if (count) { /* not first time through */
/* calculate matrices corrsponding to last position*/
anim_y_p_r2mat(m_to_world,angle,0.0,0.0);
anim_add_trans(m_to_world,front,zero);
anim_y_p_r2mat(m_from_world,-angle,0.0,0.0);
VREVERSE(temp1,front);
anim_add_trans(m_from_world,zero,temp1);
/* calculate new position for front and back axles */
/* front goes to the point, back slides along objects*/
/* current front to back axis */
MAT4X3PNT(v,m_from_world,point);/* put point in vehicle coordinates*/
if (v[1] > length) {
fprintf(stderr,"anim_turn: Distance between positions greater than length of vehicle - ABORTING\n");
break;
}
temp2[0] = v[0] - sqrt(length*length - v[1]*v[1]); /*calculate back*/
temp2[1] = temp2[2] = 0.0;
MAT4X3PNT(back,m_to_world,temp2);/*put "back" in world coordinates*/
VMOVE(front,point);
/*calculate new angle of vehicle*/
VSUB2(temp1,front,back);
angle = bn_atan2(temp1[1],temp1[0]);
}
else { /*first time through */
/*angle is already determined*/
VMOVE(front, point);
}
/*calculate turn angles and print table*/
if (turn_wheels){
if (v[0] >= 0)
sign = 1.0;
else
sign = -1.0;
yaw = bn_atan2(sign*v[1],sign*v[0]);
if (radius > VDIVIDE_TOL)
roll_ang -= sign * MAGNITUDE(v) / radius;
if (!(count%print_int))
printf("%.10g %.10g %.10g 0.0\n",time,factor*RTOD*yaw,RTOD*roll_ang);
}
else { /* print position and orientation of vehicle */
if (!(count%print_int))
printf("%.10g %.10g %.10g %.10g %.10g 0.0 0.0\n",time,front[0],front[1],front[2], RTOD * angle);
}
count++;
}
return( 0 );
}
#define OPT_STR "r:l:a:f:p:"
int get_args(argc,argv)
int argc;
char **argv;
{
int c;
while ( (c=bu_getopt(argc,argv,OPT_STR)) != EOF) {
switch(c){
case 'l':
sscanf(bu_optarg,"%lf",&length);
break;
case 'a':
sscanf(bu_optarg,"%lf",&angle);
angle *= DTOR; /* degrees to radians */
angle_set = 1;
break;
case 'r':
sscanf(bu_optarg,"%lf",&radius);
turn_wheels = 1;
break;
case 'f':
turn_wheels = 1;
sscanf(bu_optarg,"%lf",&factor);
break;
case 'p':
sscanf(bu_optarg,"%d",&print_int);
break;
default:
fprintf(stderr,"Unknown option: -%c\n",c);
return(0);
}
}
return(1);
}
+277
View File
@@ -0,0 +1,277 @@
/* C A T T R A C K . C
*
* Caternary curve routines used by anim_track.c
*
*/
#include "conf.h"
#include <math.h>
#include <stdio.h>
#include "machine.h"
#include "vmath.h"
#include "anim.h"
#define MAX_REACHED 0
#define SOLVED 1
/* the total maximum number of lowest level iterations possible is
* T_MAX_ITS*MAX_OUT_ITS*2*MAX_ITS
*/
#define MAX_ITS 25
#define MAX_OUT_ITS 25
#define T_MAX_ITS 50
/* these tolerances are guessed at, except that it seems to be important
* in elastic situations that T_TOL be significantly smaller than the others
*/
#define T_TOL 1.0e-14
#define G_TOL 1.0e-12
#define F_TOL 1.0e-12
/* HYPER_GET_X - get x value of a point which is a given distance along
* caternary curve.
* x(s) = arcsinh(a*s-sinh(a*c))/a + c
* Left to calling routine to avoid dividing by zero.
*/
fastf_t hyper_get_x(a,c, s, d, x, cos_ang)
fastf_t a, c; /* curve parameters */
fastf_t s; /* arclength value */
{
fastf_t arg, asinh_arg;
arg = a*s - sinh(a*c);
asinh_arg = log(arg + sqrt(arg*arg + 1.0));
return(asinh_arg/a + c);
}
/* HYPER_GET_S - calculate the arclength parameter of a caternary
* curve corresponding to the given value of x.
* s(x) = (sinh(a(x-c))+sinh(ac))/a
* Left to calling routime to avoid dividing by zero.
*/
fastf_t hyper_get_s(a, c, x)
fastf_t a, c, x;
{
return((sinh(a*(x-c))+sinh(a*c))/a);
}
/* HYPER_GET_Z - calculate point on the caternary curve:
* z(x) = cosh(a*(x-c))/a + b
* Left to calling routine to avoid dividing by zero.
*/
fastf_t hyper_get_z(a,b,c,x)
fastf_t a,b,c,x;
{
fastf_t z;
if (fabs(a)>VDIVIDE_TOL){
z = cosh(a*(x-c))/a + b;
} else {
z = b;
}
return(z);
}
/* HYPER_GET_ANG - calculate angle corresponding to the slope of
* caternary curve.
* z'(x) = sinh(a*(x-c))
*/
fastf_t hyper_get_ang(a,c,x)
fastf_t a,c,x;
{
fastf_t slope;
slope = sinh(a*(x-c));
return( atan2(slope, 1.0));
}
/* GET_CURVE - Find the constants a, b, and c such that the curve
* z = cosh(a*(x-c))/a + b
* is tangent to circles of radii r0 and r1 located at
* (x0,z0) and (x1,z1) and such that the curve has
* arclength delta_s between circles. Also find the angle where
* the curve touches each circle. When called successively,
* It uses the values of a,b, and c from the last call as a start.
*/
int getcurve(pa,pb,pc,pth0,pth1,delta_s, p_zero, p_one, r_zero, r_one)
fastf_t *pa, *pb, *pc; /* curve parameters */
fastf_t *pth0, *pth1; /* angle where curve contacts circle0,circle1 */
fastf_t delta_s; /* desired arclength */
fastf_t r_zero, r_one; /* radii of circle0 and circle1 */
vect_t p_zero, p_one; /* center of circle0 and circle1 */
{
int status, i, solved;
int ingetcurve();
fastf_t theta_one, theta_zero, new_theta_zero, new_theta_one;
fastf_t avg_theta_zero, avg_theta_one, arc_dist;
fastf_t tang_ang, costheta;
double stmp;
vect_t q_zero, q_one, diff;
static fastf_t last_a, last_c, last_theta_one, last_theta_zero;
static int called_before = 0;
/*first calculate angle at which tangent line would contact circles*/
VSUB2(diff,p_one,p_zero);
tang_ang = atan2(diff[Z],diff[X]);
costheta = (r_zero-r_one)/MAGNITUDE(diff);
tang_ang += acos(costheta);
if (!called_before){
theta_one = tang_ang;
theta_zero = tang_ang;
(*pa) = 1.0;
*pc = 0.5*(p_one[X]+p_zero[X]);
called_before = 1;
}
else {
theta_zero = last_theta_zero;
theta_one = last_theta_one;
*pa = last_a;
*pc = last_c;
}
status = MAX_REACHED;
for (i=0;i<T_MAX_ITS;i++){
q_zero[X] = p_zero[X] + r_zero * cos(theta_zero);
q_zero[Z] = p_zero[Z] + r_zero * sin(theta_zero);
q_one[X] = p_one[X] + r_one * cos(theta_one);
q_one[Z] = p_one[Z] + r_one * sin(theta_one);
/* determine distance taken by arc*/
arc_dist = r_zero * (tang_ang - theta_zero);
arc_dist += r_one * (theta_one - tang_ang);
ingetcurve(pa,pb,pc, delta_s-arc_dist, q_zero, q_one);
solved = 0;
/* refine theta_one */
stmp = sinh( (*pa)*(q_zero[X]-(*pc)) );
new_theta_zero = atan2(1.0,-stmp);
avg_theta_zero = 0.5 * (theta_zero + new_theta_zero);
if (fabs(theta_zero-avg_theta_zero)<T_TOL){
solved++;
}
theta_zero = avg_theta_zero;
/* refine theta_two */
stmp = sinh( (*pa)*(q_one[X]-(*pc)) );
new_theta_one = atan2(1.0,-stmp);
avg_theta_one = 0.5 * (theta_one + new_theta_one);
if (fabs(theta_one-avg_theta_one)<T_TOL){
solved++;
}
theta_one = avg_theta_one;
if (solved == 2){
status = SOLVED;
break;
}
}
last_theta_zero = theta_zero;
last_theta_one = theta_one;
last_a = *pa;
last_c = *pc;
*pth0 = theta_zero;
*pth1 = theta_one;
return(status);
}
/* INGETCURVE - find constants a, b, and c, such that the curve
* z = cosh(a*(x-c))/a + b
* passes through (x0,z0) and (x1,z1) and has arclength delta_s
* Appropriate first guesses for a,b, and c should be given.
*/
int ingetcurve(pa,pb,pc, delta_s, p_zero, p_one)
fastf_t *pa, *pb, *pc;
fastf_t delta_s;
vect_t p_zero, p_one;
{
int status, i, j, k;
fastf_t adjust;
fastf_t eff(),gee();
status = MAX_REACHED;
i=0;
while (i++<MAX_OUT_ITS){
for (j=0;j<MAX_ITS;j++){
adjust = eff(*pa,*pc,p_zero[X],p_one[X],delta_s);
if ((*pa-adjust)<=0.0){
*pa *= 0.5;
}
else {
*pa -= adjust;
}
if (adjust<F_TOL){
break;
}
}
for (k=0;k<MAX_ITS;k++){
adjust = gee(*pa,*pc,p_zero[X],p_one[X],(p_one[Z]-p_zero[Z]));
*pc -= adjust;
if (adjust<G_TOL){
break;
}
}
if ((j==0)&&(k==0)){
status = SOLVED;
break;
}
}
*pb = p_zero[Z] - cosh( (*pa)*(p_zero[X]-(*pc)) )/(*pa);
return(status);
}
/* find Newtonian adjustment for 'a', assuming 'c' fixed*/
fastf_t eff(a,c,x0,x1,delta_s)
fastf_t a,c,x0,x1,delta_s;
{
double f,fprime;
double arg0, arg1, sarg0, sarg1;
arg0 = a*(x0-c);
arg1 = a*(x1-c);
sarg0 = sinh(arg0);
sarg1 = sinh(arg1);
f = a*(sarg1-sarg0 - a*delta_s);
fprime = sarg0 - sarg1 - arg0*cosh(arg0) + arg1*cosh(arg1);
if (fabs(fprime) > VDIVIDE_TOL)
return(f/fprime);
else if ((a*a) > VDIVIDE_TOL)
return(f/(a*a));
else if (fabs(a) > VDIVIDE_TOL)
return(f/a);
else
return(f);
}
/* find Newtonian adjustment for c, assuming 'a' fixed*/
fastf_t gee(a,c,x0,x1,delta_z)
fastf_t a,c,x0,x1,delta_z;
{
double g, gprime, arg0, arg1;
arg0 = a*(x0-c);
arg1 = a*(x1-c);
g = cosh(arg1)-cosh(arg0) - a*delta_z;
gprime = a*(sinh(arg0) - sinh(arg1));
if (fabs(gprime) > VDIVIDE_TOL)
return(g/gprime);
else if (fabs(a) > VDIVIDE_TOL)
return(g/a);
else
return(g);
}
+68
View File
@@ -0,0 +1,68 @@
/* C H A N _ A D D . C
*
* Add a given value to specified columns of data.
*
* Author -
* Carl J. Nuzman
*
* Source -
* The U. S. Army Research Laboratory
* Aberdeen Proving Ground, Maryland 21005-5068 USA
*
* Distribution Notice -
* Re-distribution of this software is restricted, as described in
* your "Statement of Terms and Conditions for the Release of
* The BRL-CAD Pacakge" agreement.
*
* Copyright Notice -
* This software is Copyright (C) 1993-2004 by the United States Army
* in all countries except the USA. All rights reserved.
*/
#include <stdlib.h>
#include <unistd.h>
#include <stdio.h>
int
main(argc,argv)
int argc;
char **argv;
{
double addend, temp;
int i,j,doit, of, count, val, *col_list;
if (argc < 3) {
fprintf(stderr,"Usage: chan_add value num_columns column [column ...] < in.file > out.file\n");
return(-1);
}
sscanf(*(argv+1),"%lf",&addend);
sscanf(*(argv+2),"%d",&of);
col_list = (int *) calloc(argc-2,sizeof(int));
for (i=3;i<argc;i++){
sscanf(*(argv+i),"%d",col_list+(i-3));
}
count = 0;
while (!feof(stdin)){
val = scanf("%lf",&temp);
if (val<1)
;
else {
doit = 0;
for (j=0;j<argc-3;j++){
if (col_list[j]==count)
doit = 1;
}
if (doit)
printf("%.10g\t",temp + addend);
else
printf("%.10g\t",temp);
}
if ( count == (of-1))
printf("\n");
count = (count+1)%of;
}
return( 0 );
}
+49
View File
@@ -0,0 +1,49 @@
.TH CHAN_MULT 1 BRL/CAD
.SH NAME
chan_mult - multiply columns of data by a given factor
.PP
chan_add - add a given value to columns of data
.SH SYNOPSIS
chan_mult factor num_columns column [column column ...] < infile > outfile
.PP
chan_add value num_columns column [column column ...] < infile > outfile
.SH DESCRIPTION
.I Mult_chan
will multiply all numbers in the specified columns by the given
factor. The infile is
an ASCII file, with columns separeted by white space. The columns are
numbered from 0 to (n-1).
.I Add_chan
behaves analogously, but with
addition rather than multiplication.
.SH EXAMPLES
These routines are useful for converting between units in animation
tables.
.PP
To multiply all but the first column of a four column file by 2.54:
.PP
.B
chan_mult 2.54 4 1 2 3
.PP
To add ten to the first six columns of an eight-column file:
.PP
.B
chan_add 10.0 8 0 1 2 3 4 5
.PP
To convert the second of three columns from Fahrenheit to Celcius:
.PP
.B
chan_add -32 3 1
.br
.B
chan_mult 0.56 3 1
.SH BUGS
The files must contain numbers and whitespaces only.
.SH AUTHOR
Carl J. Nuzman
.SH COPYRIGHT
This software is Copyright (C) 1993-2004 by the United States Army
in all countries except the USA. All rights reserved.
.SH "BUG REPORTS"
Reports of bugs or problems should be submitted via electronic
mail to <CAD@ARL.ARMY.MIL>.
+67
View File
@@ -0,0 +1,67 @@
/* C H A N _ M U L T . C
*
* Multiply specified columns of data by a given factor.
*
* Author -
* Carl J. Nuzman
*
* Source -
* The U. S. Army Research Laboratory
* Aberdeen Proving Ground, Maryland 21005-5068 USA
*
* Distribution Notice -
* Re-distribution of this software is restricted, as described in
* your "Statement of Terms and Conditions for the Release of
* The BRL-CAD Pacakge" agreement.
*
* Copyright Notice -
* This software is Copyright (C) 1993-2004 by the United States Army
* in all countries except the USA. All rights reserved.
*/
#include <stdlib.h>
#include <unistd.h>
#include <stdio.h>
int
main(argc,argv)
int argc;
char **argv;
{
double factor, temp;
int i,j,doit, of, count, val, *col_list;
if (argc < 4){
fprintf(stderr,"Usage: chan_mult factor num_columnss column [col ... ] < in.file > out.file\n");
return(-1);
}
sscanf(*(argv+1),"%lf",&factor);
sscanf(*(argv+2),"%d",&of);
col_list = (int *) calloc(argc-2,sizeof(int));
for (i=3;i<argc;i++){
sscanf(*(argv+i),"%d",col_list+(i-3));
}
count = 0;
while (!feof(stdin)){
val = scanf("%lf",&temp);
if (val<1)
;
else {
doit = 0;
for (j=0;j<argc-3;j++){
if (col_list[j]==count)
doit = 1;
}
if (doit)
printf("%.10g\t",temp*factor);
else
printf("%.10g\t",temp);
}
if ( count == (of-1))
printf("\n");
count = (count+1)%of;
}
return( 0 );
}
+70
View File
@@ -0,0 +1,70 @@
.TH CHAN_PERMUTE.C 1 BRL/CAD
.SH NAME
chan_permute - operate on columns of files.
.SH SYNOPSIS
.B chan_permute
.B -i infile1 id id ...
.B [-i infile2 id ...]
.B -o outfile1 id id ...
.B [-o outfile2 id ...]
.SH DESCRIPTION
This program mixes, matches, and merges ASCII files organized in
channels or columns. Each word, separated by whitespaces, should be less
than 40 characters long. The channels in each input file are specified
and then mapped to the desired channels in the output file(s). These are
the sort of things that can be done using
.I cut
and
.I paste,
but when
working on animation tables it's often nice to be able to do it in one
step.
.PP
.BR Infile s
are files to be read from,
.BR outfile s
are files to be written
to, and each
.B id
is a small positive integer identifying a channel. All of the
input
.BR id 's
should be distinct integers, or the results are not guaranteed.
.PP
.I Chan_permute
interprets
.B -i stdin
as standard input and
.B -o stdout
as
standard output.
.SH EXAMPLES
The command
.sp
chan_permute -i foo 0 1 2 -o stdout 2 1 0
.sp
reverses the order of foo's three columns and sends them to standard output.
.sp
.sp
The command
.sp
chan_permute -i file1 0 1 -i file2 2 3 -o file3 2 0 1 -o file4 3 0 1
.sp
creates file3 and file4, each containing one of the columns of file2
followed by both columns of file1.
.SH BUGS
A given file may be referenced
more than once for input, but may not be referenced for input and output
together or output and output together. In the latter case, the second
output reference overrides the other. The
.BR id 's
must be integers
somewhere between 0 and the number of arguments, inclusive.
.SH AUTHOR
Carl J. Nuzman
.SH COPYRIGHT
This software is Copyright (C) 1993-2004 by the United States Army
in all countries except the USA. All rights reserved.
.SH "BUG REPORTS"
Reports of bugs or problems should be submitted via electronic
mail to <CAD@ARL.ARMY.MIL>.
+152
View File
@@ -0,0 +1,152 @@
/* C H A N _ P E R M U T E . C
*
* This program mixes, matches, and merges files organized in
* channels or columns.
* It's nothing cut and paste can't do, but sometimes it's nice to
* be able to do it in one step, especially when working with animation
* tables.
*Usage: channel -i infile1 id id id ... [-i infile2 ...] -o outfile1 id id ...
* [-o outfile2 ...]
*where infiles are files to be read from, outfiles are files to be written
*to, and each id is a small positive integer identifying a channel. All of the
*input id's should be distinct integers, or the results are not guaranteed.
*
* Author -
* Carl J. Nuzman
*
* Source -
* The U. S. Army Research Laboratory
* Aberdeen Proving Ground, Maryland 21005-5068 USA
*
* Distribution Notice -
* Re-distribution of this software is restricted, as described in
* your "Statement of Terms and Conditions for the Release of
* The BRL-CAD Pacakge" agreement.
*
* Copyright Notice -
* This software is Copyright (C) 1993-2004 by the United States Army
* in all countries except the USA. All rights reserved.
*/
#include "conf.h"
#ifdef USE_STRING_H
#include <string.h>
#else
#include <strings.h>
#endif
#include <stdlib.h>
#include <unistd.h>
#include <stdio.h>
#define MAXLEN 40
typedef char Word[MAXLEN];
struct unit {
FILE *file;
int channels;
short *list;
unsigned i_o; /*i=1 o=0*/
};
char ihead[] = "-i";
char ohead[] = "-o";
int
main(argc,argv)
int argc;
char **argv;
{
int i,j, maxlength,num_done;
int icount, ocount;
struct unit *x, *y;
Word *arrayd;
i=j=icount = ocount = maxlength = 0;
for(i=1;i<argc;i++){
if( !strncmp(argv[i],ihead,2) ){
j=0;
icount++;
}
else if( !strncmp(argv[i],ohead,2) ){
j=0;
ocount++;
}
else
maxlength = (++j>maxlength) ? j : maxlength;
}
y = (struct unit *) calloc(icount+ocount,sizeof(struct unit));
x = y - 1;
for(i=1;i<argc;i++){
if( !strncmp(argv[i],"-",1) ){
j=0;
x++;
x->list = (short *) calloc(maxlength,sizeof(short));
if (argv[i][1] == 'i'){
i++;
(x)->i_o = 1;
if ( ! strcmp(argv[i],"stdin") )
x->file = stdin;
else if ( !(x->file = fopen(argv[i],"r")) )
fprintf(stderr,"Channel: can't open %s\n",argv[i]);
}
else if (argv[i][1] == 'o'){
i++;
(x)->i_o = 0;
if ( ! strcmp(argv[i],"stdout") )
x->file = stdout;
else if ( !(x->file = fopen(argv[i],"w")) )
fprintf(stderr,"Channel: can't write to %s\n",argv[i]);
}
else{
fprintf(stderr,"Illegal option %c\n",argv[i][1]);
exit(-1);
}
}
else{
sscanf(argv[i],"%hd",x->list+(j++));
x->channels++;
}
}
arrayd = (Word *) calloc(argc,sizeof(Word));/*may use more memory than absolutely necessary*/
num_done = 0;
while(num_done < icount ){ /* go until all in files are done */
num_done = 0;
for (x=y;x<y+ocount+icount;x++){ /* do one line */
if(num_done >= icount)
;/*chill - all in files done */
else if (x->i_o == 1){
if(feof(x->file))
num_done += 1;
else
for(j=0;j<x->channels;j++)
fscanf(x->file,"%s ",arrayd[x->list[j]]);
}
else if (x->i_o == 0){
for(j=0;j<x->channels;j++)
fprintf(x->file,"%s\t",arrayd[x->list[j]]);
fprintf(x->file,"\n");
}
}
}
free(arrayd);
for (x=y;x<y+ocount+icount;x++){
free(x->list);
}
free(y);
exit(0);
}
int max(m,n) /*return greatest of n integers, unless one is greater than n*/
int m[],n;
{
int i,j;
j = 0;
for (i=0;i<n;i++){
j = (m[i]>j) ? m[i] : j;
}
return( (j>n) ? 0 : j );
}
-246
View File
@@ -1,246 +0,0 @@
Annotation and view-object rendering notes
==========================================
Scope
-----
BRL-CAD has two related, but deliberately distinct, ways to represent visual
markup:
* An annotation is an ID_ANNOT database primitive. It is persistent model
content with enough semantic and presentation information to be reproduced
outside the application that created it.
* A view object is application-owned scene state. It is useful for interactive
construction and manipulation, but is intentionally not backed by a database
object.
They share portions of the interactive display infrastructure, but they do not
currently have interchangeable ownership, lifetime, or rendering semantics.
Annotation capabilities
-----------------------
An rt_annot_internal stores a model-space anchor, a set of 2D vertices, and
either a model plane basis or screen-space placement. Its segment types cover
lines, circular arcs, NURBS, Beziers, text, and filled polygons. Segment style
records include a semantic role, line pattern and width, RGBA color, font or
symbol, text scaling, and decorative flags.
The libged annotate command can create styled text, leaders, linear/angular/
radius/diameter/ordinate dimensions, and bounding-box autodim groups. It can
regenerate derived annotations from saved attributes and associate them with
source model objects without making them part of those objects' CSG trees.
Annotations therefore have the properties needed for persistent markup:
* database naming, paths, transforms, and instances;
* survival across save/reopen and transfer to another application;
* semantic segment roles and per-segment presentation data;
* model-space and view-dependent screen-space placement; and
* high-level generation metadata and source-object associations.
An annotation is informational coverage, not a CSG solid. The raytracing
implementation preserves that distinction. It prepares annotation coverage
from active database paths and composites it on primary samples after ordinary
geometry has established color and depth. Model-space annotation coverage is
occluded by nearer solid geometry. Screen-space annotation coverage uses the
render view and image dimensions. Annotations do not acquire artificial
volume, alter model bounds, cast shadows, or participate in reflection and
refraction rays.
Visible coverage is returned in back-to-front layers. Model-space layers are
ordered by ray distance, followed by view-space layers ordered by projected
anchor depth; segment draw order breaks ties within an annotation. This lets
the image renderers apply source-over alpha consistently while retaining the
single-frontmost-hit query for compatibility. NIRT continues to report one
frontmost segment per model-space annotation rather than exposing these
presentation layers as solid partitions.
Color follows normal database tree state. An annotation segment with an
explicit RGBA style wins; otherwise it inherits the resolved combination-path
color; otherwise it is white. The legacy region-ID color table is not applied
to annotation display or coverage, since annotations are informational leaves
rather than regions.
Prepared coverage uses the existing libbg RTree implementation. A 3D RTree
culls model-space annotation instances and a 2D local RTree culls segments
inside every annotation. Screen-space instance extents cannot be placed in a
static world-space index because they change with the view, so those instances
remain in a compact list while still using their local segment RTree. This
avoids a new spatial data structure and keeps prepared scenes immutable and
safe for concurrent sample queries.
The rt, ART, and ADRT/ISST integrations follow this overlay model. ERT invokes
rt with the database, displayed database paths, and view, so database-backed
annotations can follow that route as well. ERT does not currently serialize
or pass application-owned view objects to its subprocess.
NIRT keeps annotation diagnostics opt-in. `useannot 1` enables model-space
annotation intersections, and the `fmt a` action reports them. Default NIRT
output is unchanged. Screen-space annotations are deliberately omitted
because a NIRT ray does not define an image size, pixel footprint, or complete
model-to-view mapping.
View-object capabilities
------------------------
The core representation is bv_scene_obj. A view set owns shared view objects,
and a particular bview can also own local objects. Independent views force
local ownership. bv_obj_put recycles objects when their application lifetime
ends; the objects are not written to the .g database.
The `view obj` command exposes the principal markup types:
* Lines are model-coordinate polylines represented by vlists. Generic scene
rendering can add arrowheads to segment ends.
* Labels have a model anchor and optional model-space target/leader. Their text
is projected and drawn as screen-facing HUD text. If the command omits Z,
screen X/Y coordinates are projected onto the current view plane at creation
time.
* Polygons include general polygons, circles, ellipses, rectangles, and
squares. Creation and editing operate on a saved view plane with a view-Z
offset. Selection, movement, open/close, area, overlap, and 2D boolean
operations are supported. A "fill" is currently a set of hatch lines, not
an opaque surface. Polygons can be explicitly imported from or exported to
persistent sketch primitives.
Scene objects also provide object color, transparency, pixel line width, dash
style, and arrow dimensions. Not all of these properties have a uniform
command interface for every object type.
There are other visual layers that should not be conflated with these objects.
Legacy gv_tcl data/sdata arrows, axes, lines, labels, and polygons have a
separate representation. Faceplate/HUD elements are screen UI. Database
objects temporarily cloned for editing are also transient, but retain database
primitive semantics and live in the database-object scene containers.
Comparison
----------
Both annotations and view objects eventually produce display-manager pixels,
often through bv_scene_obj and vlists. That common final path does not make
their source representations equivalent.
Annotations are the canonical choice when markup must be saved, named in a
database, instanced, shared, raytraced from a .g file, or understood by another
program. View objects are the right choice for application/session state that
must be created and manipulated without changing the database.
Some view objects have a direct annotation analogue, but conversion is not
lossless without type-aware logic:
* A view polyline maps naturally to line segments, including arrowhead style.
* A polygon outline and its hatch lines can map to annotation coverage, but the
existing view "fill" must not silently become an opaque filled polygon.
* A label is hybrid. Its target and leader are model-space geometry while its
glyphs remain screen-facing at a projected model anchor.
* Arbitrary vlist extraction is insufficient because display-matrix commands,
point and line sizes, child objects, glyph behavior, and semantic roles are
otherwise lost or ambiguous.
View-object line width and annotation line width also need an explicit unit
policy. View-object widths are display pixels. Screen-space annotation widths
are view-dependent coverage widths. A model-space annotation's line_width is
used as a scale on the automatically selected model-space stroke width. In
other words, removing a separate raytracer "stroke-width" setting does not
remove width control: the annotation's existing line_width/`--line-width`
style remains the single user-facing control. The renderer interprets it in
the appropriate coordinate system rather than exposing a second competing
knob.
Recommended transient rendering design
--------------------------------------
Do not make librt or the raytracers depend on bv_scene_obj, libbv application
containers, or libged. Do not manufacture tubes, TGCs, meshes, or geometry
just in front of the view plane. Artificial geometry would affect bounds,
depth, shadows, and secondary rays, and would make antialiasing and perspective
behavior depend on a fabricated distance from the eye.
If transient view objects need to appear in raytraced output, use an explicit
application-to-renderer snapshot boundary:
1. The GED/application layer snapshots selected live view objects when a render
is launched. This is the only layer that owns their lifetime and semantics.
2. A type-aware adapter in libged or libbv translates supported objects into a
renderer-neutral overlay/coverage description. It should reuse annotation
coverage preparation through an in-memory annotation-instance interface,
rather than duplicate line, glyph, and arrow intersection algorithms.
3. The snapshot travels with the exact view state: model-to-view transform,
perspective, image width and height, and sampling convention. In-process
renderers can receive it directly; subprocess rt/ERT needs an explicit
serialized side channel.
4. Raytracers composite this coverage only on primary image samples, after
geometry color and depth are known. It remains outside CSG, model bounds,
shadows, reflections, and refractions.
5. Initial support should be deliberately finite: polyline strokes and
arrowheads, label glyphs and leaders, polygon outlines, and polygon hatches.
Faceplate elements and legacy gv_tcl overlays should be separately specified
opt-in layers rather than being included accidentally.
6. Snapshot records should preserve object name and type, RGBA, visibility,
local/shared ownership, presentation units, and source identity. Unsupported
object types should produce a deliberate diagnostic or documented omission.
Application-side compositing of the interactive display-manager layer over an
ERT framebuffer is a viable smaller feature if only ERT screen captures need
view objects. It would closely reproduce the interactive view, but it would
not make the objects available to standalone rt, ART, or ISST output and should
not be presented as the general renderer solution.
Conversion between the two systems should remain explicit. Automatically
turning view objects into database annotations would violate their deliberately
transient contract. A user command to promote selected view markup to a
persistent annotation would be reasonable; polygon-to-sketch export is an
existing precedent. Conversely, a view-object editor may be used as a front
end for constructing an annotation, provided the persistence action is clear.
Maintenance findings before implementing the adapter
----------------------------------------------------
Several representation issues should be corrected before type-driven snapshot
conversion is relied upon:
* Container-selection flags (BV_DB_OBJS, BV_VIEW_OBJS, BV_LOCAL_OBJS, and
BV_CHILD_OBJS) reuse numeric bits also used for semantic s_type_flags
(BV_DBOBJ_BASED, BV_VIEWONLY, BV_LINES, and others). bv_obj_create currently
assigns its type argument to s_type_flags. A local view object consequently
acquires BV_LINES incidentally, while the line command does not explicitly
tag lines. The namespaces should be separated and every object explicitly
typed.
* Lines, labels, and polygons should have unambiguous type tags and per-type
lifecycle/extraction callbacks. Snapshot conversion must inspect typed data,
not infer semantics from a rendered vlist.
* Label construction should initialize every bv_label field deliberately,
including size, line_flag, anchor, arrow, and target. Current construction
does not establish all of those values on every path.
* The status of legacy gv_tcl overlay data should be decided explicitly:
migrate it, support it through a separate adapter, or document its exclusion.
* Screen-space annotation display and raytrace units need a parity test. The
legacy display-matrix vlist path and the ray coverage path currently express
screen offsets through different mechanisms; their apparent agreement must
be verified rather than assumed.
* Per-segment annotation colors exceed the legacy interactive vlist object's
single-color model. Uniform annotate-command colors work today, but true
multicolor interactive parity may require split scene objects or a richer
display representation.
Tests for a future adapter should cover shared and local ownership, cleanup,
label anchors and leaders, polygon holes/hatches/view-Z, perspective, pixel
width, model-space occlusion, screen-space overlay, and serialization across
the ERT subprocess boundary.
Conclusion
----------
Persistent annotations and transient view objects should continue to coexist.
The annotation coverage scene is the correct renderer-side abstraction for
both saved annotations and a future snapshot of transient markup. The
application should perform the semantic conversion and transfer a view-complete
snapshot; the renderer should treat it as primary-ray coverage, never as
invented scene geometry.
+51
View File
@@ -0,0 +1,51 @@
This is awf, the Amazingly Workable Formatter -- a "nroff -man" or
(subset) "nroff -ms" clone written entirely in (old) awk.
It is slow and has many restrictions, but does a decent job on most
manual pages and simple -ms documents, and isn't subject to AT&T's
brain-damaged licensing that denies many System V users any text
formatter at all. It is also a text formatter that is simple enough
to be tinkered with, for people who want to experiment.
Type "make r" to run a regression test, formatting the manual page
(awf.1) and comparing it to a preformatted copy (awf.1.out). Type
"make install" to install it. Pathnames may need changing.
I don't know whether awf will run on 16-bit machines. Data requirements
are modest, but I fear the programs are probably big enough to run awk
out of space.
I can't believe I really wrote this.
Henry Spencer at U of Toronto Zoology
henry@zoo.toronto.edu utzoo!henry
13 July 1990
/*
* Copyright 1990 University of Toronto. All rights reserved.
* Written by Henry Spencer.
* This software is not subject to any license of the American Telephone
* and Telegraph Company or of the Regents of the University of California.
*
* Permission is granted to anyone to use this software for any purpose on
* any computer system, and to alter it and redistribute it freely, subject
* to the following restrictions:
*
* 1. The author is not responsible for the consequences of use of this
* software, no matter how awful, even if they arise from flaws in it.
*
* 2. The origin of this software must not be misrepresented, either by
* explicit claim or by omission. Since few users ever read sources,
* credits must appear in the documentation.
*
* 3. Altered versions must be plainly marked as such, and must not be
* misrepresented as being the original software. Since few users
* ever read sources, credits must appear in the documentation.
*
* 4. This notice may not be removed or altered.
*/
As required by the above notice, you are informed that this software
has been slightly modified to become the formatter for the fallback
manual-page reading software for the BRL-CAD Package.
If you wish an unmodified copy of AWF, you should contact the original
author at the address above.
+35
View File
@@ -0,0 +1,35 @@
/*
* awf/Cakefile
*
* The actual formatter is located in "../brlman", because it needs to
* be installed in BINDIR.
*
* Note: The file "brlman/awf" needs to be modified when the definition of
* ETCDIR is changed.
*/
#include "../Cakefile.defs"
#define PRODUCTS common dev.dumb mac.man mac.ms \
pass1 pass2.base pass2.man pass2.ms pass3 \
AWF_COPYRIGHT
#define SRCDIR awf
#undef BINDIR
#define BINDIR ETCDIR
#undef BINPERM
#define BINPERM MANPERM
#define FILES /**/
#define SRCSUFF /**/
#define MANSECTION 1
#define STATIC_PRODUCTS PRODUCTS /* Force PRODUCTS into dist */
/*
* There is nothing to compile.
* The "install-prod" rule should install PRODUCTS,
* and "inst-dist" rule should take care of copying to distribution dir.
* Nothing else to do.
*/
all&:
@echo "SRCDIR: all done"
#include "../Cakefile.rules"
+212
View File
@@ -0,0 +1,212 @@
.\" Some of the stuff in this file is a bit contorted, because it's also
.\" the regression-test input.
.nr ES 5n
.de ES
.PP
.in +\\n(ESu
.nf
..
.de EE
.in -\\n(ESu
.fi
.PP
..
.de PT
.ie \\n(.$>1 .TP "\\$2"
.el .TP
.ie !'\\$1'' \\$1
.el \(bu
..
.ds Nr \fInroff\fR
.TH AWF 1 "13 July 1990"
.BY "U of Toronto"
.SH NAME
awf \- amazingly workable (text) formatter
.SH SYNOPSIS
.B awf
.BI \-m acros
[ file ] ...
.SH DESCRIPTION
.if t .tm OOPS -- AWF THINKS IT'S TROFF!!!
.I Awf
formats the text from the input \fIfile\fR(s)
(standard input if none)
in an imitation of
\*(Nr's style with the \fB\-man\fR or \fB\-ms\fR macro packages.
The
.BI \-m acro
option is mandatory and must be `\-man' or `\-ms'.
.PP
.I Awf
implements the following raw \*(Nr requests:
.LP
.\e" .ce .fi .in .ne .pl .sp
.ad .de .ft .it .nf .po .ta
.bp .ds .ie .ll .nr .ps .ti
.br .el .if .na .ns .rs .tm
.LP
and the following in-text codes:
.ES
\e$ \e% \e* \ec \ef \en \es
.EE
plus the full list of \*(Nr/\c
.I troff
special characters in
the original V7 \fItroff\fR manual.
.PP
Many restrictions are present; the behavior in general is a subset of
\*(Nr's. Of particular note are the following:
.IP \(bu 2
Point sizes do not exist;
.B .ps
and
.B \es
are ignored.
.PT
Conditionals implement only numeric comparisons on
.BR \en(.$ ,
string com\%par\%isons between a macro parameter and a literal,
and
.B n
(always true)
and
.BR t
(always false).
.PT
The implementation of strings is generally primitive.
.IP \(bu
Expressions in (e.g.)\&
.B .sp
are fairly general, but the
.BR | ,
.BR & ,
and
.BR :\&
operators do not exist, and the implementation of
.B \ew
requires that quote (') be used as the delimiter and
simply counts the characters inside (so that, e.g.,
\ew'\e(bu'
equals 4).
.P
White space at the beginning of lines,
and imbedded white space within lines, is dealt with properly.
Sentence terminators at ends of lines are understood to imply
extra space afterward in filled lines.
Tabs are im\%plemented crudely and not quite correctly, although
in most cases they work as expected.
Hyphenation is done only at explicit hyphens, em-dashes, and \*(Nr
discretionary hyphens.
.SH "MAN MACROS"
The
.B \-man
macro set implements the full V7 manual macros,
plus a few semi-random oddballs.
The full list is:
.ES
\&.B .DT .IP .P .RE .SM
\&.BI .HP .IR .PD .RI .TH
\&.BR .I .LP .PP .RS .TP
\&.BY .IB .NB .RB .SH .UC
.EE
.B .BY
and
.B .NB
each take a single string argument (respectively, an indi\%cation of
authorship and a note about the status of the manual page) and arrange
to place it in the page footer.
.SH "MS MACROS"
The
.B \-ms
macro set is a substantial subset of the V7 manuscript macros.
The implemented macros are:
.ES
\&.AB .CD .ID .ND .QP .RS .UL
\&.AE .DA .IP .NH .QS .SH .UX
\&.AI .DE .LD .NL .R .SM
\&.AU .DS .LG .PP .RE .TL
\&.B .I .LP .QE .RP .TP
.EE
Size changes are recognized but ignored, as are
.B .RP
and
.BR .ND .
.B .UL
just prints its argument in italics.
.BR .DS / .DE
does not do a keep,
nor do any of the other macros that normally imply keeps.
.PP
Assignments to the header/footer string variables are recognized and
implemented, but there is otherwise no control over header/footer
formatting.
The
.B DY
string variable is available.
The
.BR PD ,
.BR PI ,
and
.BR LL
number registers exist and can be changed.
.SH OUTPUT
The only output format supported by
.IR awf ,
in its distributed form,
is that appropriate to a dumb terminal,
using overprinting for italics (via underlining) and bold.
The \*(Nr special characters are printed as some vague approximation
(it's sometimes very vague) to their correct appearance.
.PP
.IR Awf 's
knowledge of the output device is established by a device file,
which is read before the user's input.
It is sought in
.IR awf 's
library directory, first as
.BI dev. term
(where \fIterm\fR is the value of the TERM environment variable)
and, failing that, as
.BR dev.dumb .
The device file
uses special internal commands
to set up resolution, special characters, fonts, etc.,
and more normal \*(Nr commands to set up page length etc.
.SH FILES
All in \fI/usr/lib/awf\fR (this can be overridden by the AWFLIB
environment variable):
.ta \w'pass2.base'u+((3n-1n)/2u)
.nf
common common device-independent initialization
dev.* device-specific initialization
mac.m* macro packages
pass1 macro substituter
pass2.base central formatter
pass2.m* macro-package-specific bits of formatter
pass3 line and page composer
.SH SEE ALSO
awk(1), nroff(1), man(7), ms(7)
.SH DIAGNOSTICS
.na
Unlike
.IR nroff ,
.I awf
complains whenever it sees unknown commands and macros.
All diagnostics (these and some internal ones) appear on standard error
at the end of the run.
.ad
.SH HISTORY
Written at University of Toronto by Henry Spencer,
more or less as a supplement to the C News project.
.LP
.ce 99
\(rh None of the above really want to admit it. \(lh
.ce 0
.SH BUGS
There are plenty, but what do you expect for a text formatter
written entirely in (old) \fIawk\fR?
.PP
The
.B \-ms
stuff has not been checked out very thoroughly.
+7
View File
@@ -0,0 +1,7 @@
.\" Common startup code, fully device-independent.
.\" --------------------------------
.fi
.ce 0
.ta +5 +5 +5 +5 +5 +5 +5 +5 +5 +5 +5 +5 +5 +5 +5 +5 +5 +5 +5 +5 +5 +5 +5 +5 +5
.in 0
.ti 0
+154
View File
@@ -0,0 +1,154 @@
.\" Device-dependent but not macro-set-dependent definitions.
.\" --------------------------------
.\" overall formatting initialization
.\" 12 cpi horizontal exploits 80-column terminal well (6.5i@12 = 78)
.^r cpi 12 6
.\" call margin adjustment device-dependent for sake of some unusual cases
.ad
.\" page parameters
.pl 11i
.ll 6.5i
.po 0
.\" --------------------------------
.\" fonts, and their hyphens, last font change doubled to set up \fP
.^f R
.ft R
.^c hy 1 -
.^f I
.ft I
.^c hy 1 -
.^f B
.ft B
.^c hy 1 -\b-\b-
.ft R
.ft R
.\" --------------------------------
.\" definitions of nroff special characters
.\" The character definitions here operate on the "better ugly than invisible"
.\" principle, and try to approximate the character *somehow*. They were
.\" tuned for a Teletype 40 line printer, but should give vaguely plausible
.\" results on any overprinting ASCII device.
.\"
.\" first, things that nroff considered builtins
.^c \ 1 \\
.^c e 1 \\
.^c ' 1 '
.^c ` 1 `
.^c - 1 -
.\" some things seem to assume that \+ is like \-
.^c + 1 +
.\" we do not do backslash-space here, it can't be done with .^c, but the
.\" other forms of space we can do
.^c 0 1 "
.^c | 0
.^c ^ 0
.^c & 0
.\"
.\" and more normal characters
.\" note, the hyphenation logic knows about em
.^c em 2 --
.\" hy is a special case, see above
.^c bu 1 +\bo
.^c sq 2 []
.^c ru 1 _
.^c 12 3 1/2
.^c 14 3 1/4
.^c 34 3 3/4
.^c de 1 '\b`
.^c dg 1 -\b!
.^c fm 1 '
.^c ct 1 /\bc
.^c rg 3 (R)
.^c co 3 (c)
.^c pl 1 +
.^c mi 1 -
.^c eq 1 =
.^c ** 1 *
.^c sc 1 j\bf
.^c aa 1 '
.^c ga 1 `
.^c ul 1 _
.^c sl 1 /
.^c *a 1 <\ba
.^c *b 1 ,\bB
.^c *g 1 ,\by
.^c *d 1 S\bo
.^c *e 1 -\bc
.^c *z 1 ,\bL
.^c *y 1 ,\bn
.^c *h 1 -\b0
.^c *i 1 ,\bi
.^c *k 1 <\bK
.^c *l 1 \\\b>
.^c *m 1 ,\bu
.^c *n 1 ,\bv
.^c *c 1 ,\b3
.^c *o 1 o
.^c *p 1 -\bn
.^c *r 1 p
.^c *s 1 -\bo
.^c ts 1 s
.^c *t 1 ~\bt
.^c *u 1 u
.^c *f 1 /\bo
.^c *x 1 /\b\\
.^c *q 1 |\bu
.^c *w 1 u\bw
.^c *G 2 ~\b|~
.^c *D 2 _\b/_\b\\
.^c *H 1 -\bO
.^c *L 2 /\\
.^c *C 1 _\b-\b~
.^c *P 2 ~\b|~\b|
.^c *S 1 ~\b_\b>
.^c *U 1 Y
.^c *F 1 |\bO
.^c *Q 1 |\bU
.^c *W 2 _\b(_\b)
.^c sr 2 \\/
.^c rn 1 ~
.^c >= 1 _\b>
.^c <= 1 _\b<
.^c == 1 _\b=
.^c ~= 1 ~\b=
.^c ap 1 ~
.^c != 1 /\b=
.^c -> 2 ->
.^c <- 2 <-
.^c ua 1 |\b^
.^c da 1 |\bv
.^c mu 1 x
.^c di 1 -\b:
.^c +- 1 _\b+
.^c cu 1 U
.^c ca 3 (^)
.^c sb 2 (_\b~
.^c sp 2 _\b~)
.^c ib 2 (~\b_\b=
.^c ip 2 ~\b_\b=)
.^c if 2 oo
.^c pd 1 3\bo
.^c gr 1 ~\bV
.^c no 1 -
.^c is 1 '\b,\bI
.^c pt 2 oc
.^c es 1 /\bO
.^c mo 1 -\bC
.^c br 1 |
.^c dd 1 I\b|
.^c rh 1 =\b>
.^c lh 1 =\b<
.^c bs 4 (:-)
.^c or 1 |
.^c ci 1 O
.^c lt 1 ~\b(
.^c lb 1 _\b(
.^c rt 1 ~\b)
.^c rb 1 _\b)
.^c lk 1 -\b(
.^c rk 1 -\b)
.^c bv 1 |
.^c lf 1 _\b[
.^c rf 1 _\b]
.^c lc 1 ~\b[
.^c rc 1 ~\b]
+141
View File
@@ -0,0 +1,141 @@
.\"-----------------
.de TH
.ds LH "\\$1(\\$2)
.ds CH "Unix Programmer's Manual
.ds RH "\\$1(\\$2)
.ds LF "
.ds CF "\\$3
.ds RF "%
..
.\"-----------------
.de NB
.ds nb "\\$1
.lF
..
.\"-----------------
.de BY
.ds by "\\$1
.lF
..
.\"-----------------
.de UC
.BY "\\$1BSD"
..
.\"-----------------
.\" common initialization for headers and paragraphs: .In need
.de In
.ne \\$1
.sp \\n(PDu
.fi
.in \\n(inu
.ti 0
.it
.ft R
.ns
..
.\"-----------------
.de SH
.In 6
.in 0
.ft B
\&\\$1 \\$2 \\$3 \\$4 \\$5 \\$6 \\$7 \\$8 \\$9
.ft R
.nr in 5n
.in \\n(inu
..
.\"-----------------
.de LP
.In 4
..
.\"-----------------
.de PP
.LP
..
.\"-----------------
.de P
.LP
..
.\"-----------------
.de HP
.In 4
.ti 0-\\n(tpu
..
.\"-----------------
.de TP
.In 4
.if \\n(.$>0 .nr tp \\$1n
.in \\n(inu+\\n(tpu
.ti 0-\\n(tpu
.it 1 tP
..
.\"-----------------
.de IP
.ie \\n(.$>1 .TP "\\$2"
.el .TP
\&\\$1
..
.\"-----------------
.de I
.ft I
.it 1 fP
.if \\n(.$>0 \&\\$1 \\$2 \\$3 \\$4 \\$5 \\$6 \\$7 \\$8 \\$9
..
.\"-----------------
.de B
.ft B
.it 1 fP
.if \\n(.$>0 \&\\$1 \\$2 \\$3 \\$4 \\$5 \\$6 \\$7 \\$8 \\$9
..
.\"-----------------
.de IR
\&\\fI\\$1\\fR\\$2\\fI\\$3\\fR\\$4\\fI\\$5\\fR\\$6\\fI\\$7\\fR\\$8\\fI\\$9\\fR
..
.\"-----------------
.de RI
\&\\$1\\fI\\$2\\fR\\$3\\fI\\$4\\fR\\$5\\fI\\$6\\fR\\$7\\fI\\$8\\fR\\$9
..
.\"-----------------
.de BR
\&\\fB\\$1\\fR\\$2\\fB\\$3\\fR\\$4\\fB\\$5\\fR\\$6\\fB\\$7\\fR\\$8\\fB\\$9\\fR
..
.\"-----------------
.de RB
\&\\$1\\fB\\$2\\fR\\$3\\fB\\$4\\fR\\$5\\fB\\$6\\fR\\$7\\fB\\$8\\fR\\$9
..
.\"-----------------
.de BI
\&\\fB\\$1\\fI\\$2\\fB\\$3\\fI\\$4\\fB\\$5\\fI\\$6\\fB\\$7\\fI\\$8\\fB\\$9\\fR
..
.\"-----------------
.de IB
\&\\fI\\$1\\fB\\$2\\fI\\$3\\fB\\$4\\fI\\$5\\fB\\$6\\fI\\$7\\fB\\$8\\fI\\$9\\fR
..
.\"-----------------
.de SM
.\" no-op
.if \\n(.$>0 \&\\$1 \\$2 \\$3 \\$4 \\$5 \\$6 \\$7 \\$8 \\$9
..
.\"-----------------
.de DT
.ta +5 +5 +5 +5 +5 +5 +5 +5 +5 +5 +5 +5 +5 +5 +5 +5 +5 +5 +5 +5 +5 +5 +5 +5 +5
..
.\"-----------------
.de RS
.in +5n
..
.\"-----------------
.de RE
.in -5n
..
.\"-----------------
.de PD
.ie \\n(.$=0 .nr PD 0.3v
.el .nr PD \\$1n
..
.\"-----------------
.\" misc. initialization
.nr tp 5n
.PD
.ds R \(rg
.ds S "
.ds Tm (TM)
+206
View File
@@ -0,0 +1,206 @@
.\"-----------------
.de R
.ie \\n(.$=0 .ft R
.el \\fR\\$1\\fP\\$2
..
.\"-----------------
.de I
.ie \\n(.$=0 .ft I
.el \\fI\\$1\\fP\\$2
..
.\"-----------------
.de B
.ie \\n(.$=0 .ft B
.el \\fB\\$1\\fP\\$2
..
.\"-----------------
.de UX
.\" old-fashioned capitalization -- I've never gotten used to the new one
\\$2Unix\\$1
..
.\"-----------------
.de DA
.ds DY "\\$1 \\$2 \\$3
.\" keep trailing spaces out of CF
.if \\n(.$=1 .ds CF "\\$1
.if \\n(.$=2 .ds CF "\\$1 \\$2
.if \\n(.$>2 .ds CF "\\$1 \\$2 \\$3
..
.\"-----------------
.de ND
.\" it's our default, ignore it
..
.\"-----------------
.de TL
.rs
.sp 5
.ft B
.ce 9999
..
.\"-----------------
.de AU
.sp 2
.ft R
..
.\"-----------------
.de AI
.sp
.ft R
..
.\"-----------------
.de AB
.sp 2
.ce 0
.ll -7n
.in +7n
..
.\"-----------------
.de AE
.sp
.ll
.in
..
.\"-----------------
.\" common initialization for headers and paragraphs: .In need extraspace
.de In
.ne \\$1
.sp \\n(Tsu
.nr Ts 0
.ie \\n(.$>1 .nr iN \\$2v
.el .nr iN 0
.sp \\n(PDu+\\n(iNu
.ce 0
.ft R
.in \\n(inu
.ll \\n(LLu
.ns
.fi
.ti 0
..
.\"-----------------
.de SH
.nr in 0
.In 6 1
.ft B
..
.\"-----------------
.de NH
.nr in 0
.In 6 1
.ft B
.\" punt to awk code to get the header numbering right
.nH \\$1
.\" and pick up the result
\&\\*(Nh
..
.\"-----------------
.de LP
.In 4
..
.\"-----------------
.de PP
.In 4
.ti \\n(PIu
..
.\"-----------------
.de TP
.In 4
.if \\n(.$>0 .nr tp \\$1n
.in \\n(inu+\\n(tpu
.ti 0-\\n(tpu
.it 1 tP
..
.\"-----------------
.de IP
.ie \\n(.$>1 .TP "\\$2"
.el .TP
\&\\$1
..
.\"-----------------
.de QP
.In 4
.in +5n
.ll -5n
..
.\"-----------------
.de QS
.nr in +5n
.nr LL -5n
.In 4
..
.\"-----------------
.de QE
.nr in -5n
.nr LL +5n
.In 4
..
.\"-----------------
.de DS
.In 5
.if '\\$1'C' .ce 9999
.if '\\$1'' .in +5n
.nf
..
.\"-----------------
.de CD
.In 5
.ce 9999
.nf
..
.\"-----------------
.de LD
.In 5
.nf
..
.\"-----------------
.de ID
.In 5
.in +5n
.nf
..
.\"-----------------
.de DE
.In 3
..
.\"-----------------
.de RS
.nr in +5n
.in \\n(inu
..
.\"-----------------
.de RE
.nr in -5n
.in \\n(inu
..
.\"-----------------
.de UL
\&\\fI$1\\fP
..
.\"-----------------
.de RP
..
.\"-----------------
.de LG
..
.\"-----------------
.de SM
..
.\"-----------------
.de NL
..
.\"-----------------
.\" the -ms accent strings
.ds ' "'\b
.ds ` "`\b
.ds : ":\b
.ds ^ "^\b
.ds ~ "~\b
.ds C "v\b
.ds , ",\b
.\" post-title spacing
.nr Ts 4v
.\" and parameter setup
.nr LL 6i
.ll \n(LLu
.nr PD 0.3v
.nr PI 5n
+212
View File
@@ -0,0 +1,212 @@
# first pass: macro expansion and .if
# We support macros, conditionals (of three quite limited forms), and macro
# argument substitution.
BEGIN {
curmacro = ""
macros[""] = 0 # just to make it an array
macrolen[""] = 0 # just to make it an array
macrotext[0] = "" # just to make it an array
args[""] = "" # just to make it an array
ntext = 1 # first slot in macrotext; cannot be 0
nroffset = 0 # offset between NR and "real" line numbers
inname = "?" # input filename
sp = 0 # stack "pointer" (number of stacked macros)
maxsp = 25 # limit on nesting depth
macrostack[sp] = "" # to make it an array
nleftstack[sp] = "" # to make it an array
ptrstack[sp] = "" # to make it an array
nargstack[sp] = "" # to make it an array
argstack[sp] = "" # to make it an array
condstack[sp] = "" # to make it an array
}
/^\.\^#/ { # filename and line no of next line: .^# no fn
nroffset = (NR+1) - $2
inname = $3
print
next
}
/^\.de/ { # macro start
curmacro = "." $2
macros[curmacro] = ntext
macrostart = ntext
next
}
curmacro != "" && $0 !~ /^\.\.$/ { # macro text - \\ becomes \
if ($0 !~ /\\/) # quick case, no backslashes
line = $0
else {
line = ""
for (n = 1; n <= length; n++) {
if (substr($0, n, 2) == "\\\\")
n++
line = line substr($0, n, 1)
}
}
macrotext[ntext++] = line
next
}
curmacro != "" && $0 ~ /^\.\.$/ { # macro end
macrolen[curmacro] = ntext - macrostart
curmacro = ""
print ".^#", NR - nroffset + 1, inname
next
}
$0 ~ /^\./ && ( macros[$1] != 0 || $0 ~ /^\.(i[ef]|el)/ ) {
# something that needs attention
print ".^=", NR - nroffset, inname
line = $0
nleft = 0
macro = "<none>"
nargs = 0
while (line != "") {
# conditionals; note that 1-n is !n (awk doesn't have !)
invert = 0
if (line ~ /^\.i[ef] !/)
invert = 1
prevcond = cond
cond = 0
if (line !~ /^\.(i[ef]|el)/) { # not conditional
cond = 1
iflen = 0
} else if (line ~ /^\.i[ef] !?\\n\(\.\$[<=>][0-9] /) {
# arithmetic comparison on arg count
iflen = length(".if .n(.$=x ") + invert
n = substr(line, iflen-1, 1) + 0
op = substr(line, iflen-2, 1)
if (op == "=" && nargs == n)
cond = 1
else if (op == "<" && nargs < n)
cond = 1
else if (op == ">" && nargs > n)
cond = 1
} else if (line ~ /^\.i[ef] !?'\\\$[0-9]'[^']*' /) {
# string equality on argument
iflen = length(".if '.$n'") + invert
n = substr(line, iflen-1, 1)+0
if (n <= nargs)
s1 = args[n]
else
s1 = ""
i = index(substr(line, iflen+1), "'")
s2 = substr(line, iflen+1, i-1)
iflen += i+1
if (s1 == s2)
cond = 1
} else if (line ~ /^\.i[ef] !?[nt] /) {
# nroff vs troff
iflen = length(".if n ") + invert
if (substr(line, iflen-1, 1) == "n")
cond = 1
} else if (line ~ /^\.el /) {
cond = 1 - prevcond
iflen = length(".el ")
} else {
line = ".tm unknown .if/.ie form: " line
cond = 1
iflen = 0
}
if (invert)
cond = 1 - cond
if (cond && iflen > 0) # trim true conditional off
line = substr(line, iflen+1)
# do argument substitution, if necessary
if (cond && line ~ /\\\$/) {
orig = line
line = ""
for (pos = index(orig, "\\$"); pos > 0; \
pos = index(orig, "\\$")) {
if (pos > 1)
line = line substr(orig, 1, pos-1)
c = substr(orig, pos+2, 1)
if (c ~ /[0-9]/ && c+0 <= nargs)
line = line args[c+0]
orig = substr(orig, pos+3)
}
line = line orig # the remnant
}
# is it an nroff command?
if (cond && line ~ /^\./) {
cmd = substr(line, 1, 3)
while (cmd ~ / $/)
cmd = substr(cmd, 1, length(cmd)-1)
} else
cmd = ""
# deal with it
if (!cond)
nop = 0 # nothing
else if (cmd == "" || macros[cmd] == 0)
print line # not a nested macro
else if (sp >= maxsp)
print ".tm macros nested too deeply (" sp " levels)"
else { # nesting
# stack old one
sp++
nleftstack[sp] = nleft
ptrstack[sp] = ptr
macrostack[sp] = macro
nargstack[sp] = nargs
condstack[sp] = cond
for (i = 1; i <= nargs; i++)
argstack[sp ":" i] = args[i]
# start new one, mostly pulling arguments apart
macro = cmd
nleft = macrolen[macro]
ptr = macros[macro]
cond = 0
argno = 1
pos = length(macro) + 1
for (;;) {
while (substr(line, pos, 1) ~ /[ \t]/)
pos++
if (pos > length(line))
break # NOTE BREAK OUT
arg = ""
if (substr(line, pos, 1) == "\"") {
pos++
while (substr(line, pos, 1) ~ /[^"]/) {
arg = arg substr(line, pos, 1)
pos++
}
pos++
} else
while (substr(line, pos, 1) ~ /[^ \t]/) {
arg = arg substr(line, pos, 1)
pos++
}
args[argno++] = arg
}
nargs = argno - 1
}
# clean up any completed macros
while (nleft <= 0 && sp > 0) {
nleft = nleftstack[sp]
ptr = ptrstack[sp]
macro = macrostack[sp]
nargs = nargstack[sp]
cond = condstack[sp]
for (i = 1; i <= nargs; i++)
args[i] = argstack[sp ":" i]
sp--
}
# finally, get next line
if (nleft > 0) {
line = macrotext[ptr++]
nleft--
} else
line = "" # signal loop to terminate
}
print ".^#", NR - nroffset + 1, inname
next
}
{
# it's ordinary
print
}
+587
View File
@@ -0,0 +1,587 @@
# second pass: interpretation of directives
# A macro-set-specific portion gets interpolated into this at the "#include"
# line. As a minimum, it must deal with .^b and .^e and with any input traps.
BEGIN {
# stuff for output to third pass
nobreak = -1
dobreak = -2
message = -3
OFS = "\t"
# special-character table; this one character needs to be hardcoded
chars[" "] = " " ; charwidths[" "] = 1
debug["e"] = 0 # just to make it an array
strings["a"] = "" # just to make it an array
numbers["a"] = 0 # just to make it an array
hyphens["a"] = "" # just to make it an array
hyphenwidths["a"] = "" # just to make it an array
# stuff for expression decoding
signfactor["+"] = 1
signfactor["-"] = -1
scale["i"] = 240
scale["c"] = 240*50/127
scale["P"] = 240/6
# we get m, n, and v when we see .^r
scale["p"] = 240/72
scale["u"] = 1
# stuff for basic parameters that just get passed to third pass
parms["in"] = 0 # just to make it an array
prevparms["in"] = 0 # just to make it an array
setcmd["ll"] = "linelen"
setcmd["in"] = "indent"
setcmd["ti"] = "tempindent"
setcmd["po"] = "pageoffset"
setcmd["pl"] = "pagelen"
# did last word end with \c ? (in which case, it's still in "word")
backc = 0
# stuff for error reporting
il = 0 # input line number
lockil = 0 # il is locked, we're inside a macro
inname = "?" # input filename
msg = message "\t" # later picks up filename etc.
# current input trap
afternext = ""
}
{
if (!lockil)
il++
msg = message "\t" inname "," il ": "
# fallthrough
}
/^[ \t]*$/ { # empty line
print dobreak, "space"
next
}
/^[ \t]/ { # line starting with white space
print dobreak, "flush"
print 0, "" # empty word
# fallthrough
}
/^[^.]/ { # text
# dispose of the easy case
if (font == "R" && $0 !~ /\\|\t|-| / && !backc && afternext == "") {
for (i = 1; i <= NF; i++)
print length($i), $i
if ($0 ~ /[.!?:]([)'"*]|])*$/)
print nobreak, "gap", 2
if (centering > 0) {
print dobreak, "center"
centering--
} else if (!fill)
print dobreak, "flush"
next
}
# the hard case, needs a character-by-character scan
s = $0 " " # the space flushes the last word
n = 1 # current position in s
inword = 0 # have we been processing a word?
period = "" # "." if this word ended a sentence
nsp = 0 # count of spaces seen so far
tabpos = 0 # which tab position was used last
while (n <= length(s)) {
c = substr(s, n, 1)
# handle state transitions
if (c == " " || c == "\t") {
if (inword) { # ends word
if (!backc) {
print wordlen, word
if (usedhyphen)
print nobreak, "nohyphen"
}
inword = 0
nsp = 0
}
} else {
if (!inword) { # begins word
if (!backc) {
word = ""
wordlen = 0
usedhyphen = 0
}
backc = 0
inword = 1
if (nsp > 1)
print nobreak, "gap", nsp
}
}
# deal with the character
if (c == " ") {
nsp++
if (n != length(s)) # not the trailing flusher
period = ""
} else if (c == "\t") {
# not really right, should be based on input position
# also, one space following tab gets ignored
tabpos++
if (tabpos <= ntabs)
print nobreak, "tabto", tabs[tabpos]
nsp = 0
period = ""
} else if (c == "-" && wordlen > 0) {
# hyphen within word
print wordlen, word, hyphenwidths[font]
print nobreak, "userhyphen", hyphens[font], hyphenwidths[font]
word = ""
wordlen = 0
period = ""
usedhyphen = 1
} else if (c != "\\") {
# ordinary character
if (font == "B")
word = word c "\b" c "\b" c
else if (font == "I" && c ~ /[a-zA-Z0-9]/)
word = word "_\b" c
else
word = word c
wordlen++
if (c ~ /[.!?:]/)
period = "."
else if (c !~ /([)'"*]|])/)
period = ""
} else { # backslash
n++
c = substr(s, n, 1)
if (c == "f") {
# font change
n++
code = substr(s, n, 1)
if (code == "(") {
n++
code = substr(s, n, 2)
n++
}
if (code == "P")
font = prevfont
else if (fontok[code] == "")
print msg "unknown font `" code "'"
else {
prevfont = font
font = code
}
} else if (c == "n") {
# number-register value
n++
code = substr(s, n, 1)
if (code == "(") {
n++
code = substr(s, n, 2)
n++
}
s = substr(s, 1, n) numbers[code] substr(s, n+1)
} else if (c == "s") {
# size change
n++
if (substr(s, n, 1) ~ /[0-9]/)
n++
# just ignore it
} else if (c == "c")
# word continuation
backc = 1
else if (c == "*") {
# string-variable value
n++
code = substr(s, n, 1)
if (code == "(") {
n++
code = substr(s, n, 2)
n++
}
s = substr(s, 1, n) strings[code] substr(s, n+1)
} else if (c == "%") {
# discretionary hyphen
if (wordlen > 0) {
print wordlen, word, hyphenwidths[font]
print nobreak, "hyphen", hyphens[font], hyphenwidths[font]
word = ""
wordlen = 0
usedhyphen = 1
}
} else if (c == "(" && substr(s, n+1, 2) == "em" && \
chars["em"] != "") {
# em-dash, special case due to hyphenation
n += 2
emw = charwidths["em"]
print wordlen, word, emw
print nobreak, "userhyphen", chars["em"], emw
word = ""
wordlen = 0
period = ""
usedhyphen = 1
} else {
# special-character name
code = c
if (code == "(") {
n++
code = substr(s, n, 2)
n++
}
word = word chars[code]
wordlen += charwidths[code]
period = ""
}
}
# on to the next character, at last
n++
}
# end-of-line processing
if (!backc) {
if (period == ".")
print nobreak, "gap", 2
if (centering > 0) {
print dobreak, "center"
centering--
} else if (!fill)
print dobreak, "flush"
}
# if no input trap, we're done
if (afternext == "")
next
# if there is an input trap, fall into the macro-dependent section
}
#
#
#
# at this point we plug in the macro-specific stuff, keyed on the next line
#include note that this is an awk comment
#
#
#
/^\.it/ { # plant an input trap, sort of
if (NF > 1 && $2 != 1)
print msg ".it first argument must be 1"
if (NF > 2)
afternext = afternext "," $3
else
afternext = ""
next
}
/^\.\^r cpi / { # set resolutions, in cpi: .^r cpi hor vert
scale["m"] = 240/$3
scale["n"] = 240/$3
scale["v"] = 240/$4
next
}
/^\.(ta|ll|in|ti|po|ne|sp|pl|nr)/ { # expression processing
# sort out default scale factor
if ($1 ~ /^\.(ne|sp|pl)/)
exprscale = "v"
else if ($1 ~ /^\.(nr)/)
exprscale = "u"
else
exprscale = "n"
# which argument should we start with?
offset = length($1) + 1
if ($1 == ".nr")
offset += length($2) + 1
# beginning of debugging message
if (debug["e"])
printf "%s ", msg substr($0, 1, offset)
# do the expressions
s = substr($0, offset+1)
n = 1
while (s != "") {
while (s ~ /^[ \t]/)
s = substr(s, 2)
# an initial sign is magic
ssign = ""
if (s ~ /^[+-]/) {
ssign = substr(s, 1, 1)
s = substr(s, 2)
}
s = "+" s # this is an un-magic addition operator
# process terms
sval = 0
while (s ~ /^([+*%)-]|\/)/) {
# figure out what it is and what it contributes
if (debug["e"] > 1)
print "s=`" s "'"
termop = substr(s, 1, 1)
s = substr(s, 2)
termscale = exprscale
if (termop == ")") {
if (debug["e"] > 1)
print "pop " valstack[vsp] " " opstack[vsp] " with " sval
termval = sval
sval = valstack[vsp]
termop = opstack[vsp]
vsp--
termscale = "u"
} else if (s ~ /^\(/) {
if (debug["e"] > 1)
print "push " sval " " termop
vsp++
valstack[vsp] = sval
opstack[vsp] = termop
sval = 0
termop = "+" # dummy op and value
termval = 0
s = "+" substr(s, 2)
} else if (s ~ /^\\w/) {
delim = substr(s, 3, 1)
s = substr(s, 4)
endp = index(s, delim)
if (endp == 0)
endp = length(s) + 1
termval = (endp - 1) * scale["n"] # crude
s = substr(s, endp+1)
} else if (s ~ /^\\n/) {
if (s ~ /^\\n\(/) {
code = substr(s, 4, 2)
s = substr(s, 6)
} else {
code = substr(s, 3, 1)
s = substr(s, 4)
}
termval = numbers[code]
} else if (s ~ /^[0-9.]/) {
for (endp = 1; endp <= length(s); endp++)
if (substr(s, endp, 1) !~ /[0-9.]/)
break
termval = substr(s, 1, endp-1) + 0
s = substr(s, endp)
}
# add it in, with scaling factor
c = substr(s, 1, 1)
if (scale[c] != "") {
termval *= scale[c]
s = substr(s, 2)
} else
termval *= scale[termscale]
if (termop == "+")
sval += termval
else if (termop == "-")
sval -= termval
else if (termop == "*")
sval *= termval
else if (termop == "/")
sval = int(sval) / int(termval)
else if (termop == "%")
sval = int(sval) % int(termval)
}
# remember the value, print if debugging
expr[n] = sval
exprsign[n] = ssign
iexpr[n] = signfactor[ssign] * sval # convenience
if (debug["e"])
printf "%s ", ssign "(" sval ")"
# proceed to next, skipping trash if necessary
while (s ~ /^[^ \t]/)
s = substr(s, 2)
n++
}
# final cleanup
nexprs = n - 1
if (debug["e"])
printf "\n"
# fallthrough
}
/^\.(ll|in|ti|po|pl)/ { # common code for set-parameter requests
# relies on expression processing, including setting of exprscale
name = substr($1, 2, 2)
n = parms[name]
if (nexprs == 0)
n = prevparms[name]
else if (exprsign[1] == "" || name == "ti")
n = expr[1] / scale[exprscale]
else
n += iexpr[1] / scale[exprscale]
prevparms[name] = parms[name]
parms[name] = int(n)
print dobreak, setcmd[name], parms[name]
next
}
/^\.nr/ {
# relies on expression processing
n = numbers[$2]
if (exprsign[1] == "")
n = expr[1]
else
n += iexpr[1]
numbers[$2] = int(n)
next
}
/^\.ne/ {
# relies on expression processing
print dobreak, "need", int(expr[1]/scale["v"] + 0.99)
next
}
/^\.sp/ {
# relies on expression processing
if (nexprs == 0)
i = 1
else
i = int(expr[1]/scale["v"] + 0.99)
for (; i > 0; i--)
print dobreak, "space"
next
}
/^\.ta/ {
# relies on expression processing
tabstop = 0
for (n = 1; n <= nexprs; n++) {
if (exprsign[n] == "")
tabstop = expr[n]
else
tabstop += iexpr[n]
tabs[n] = int(tabstop/scale["n"])
}
ntabs = nexprs
next
}
/^\.ft/ {
if (NF > 1)
code = $2
else
code = "P"
if (code == "P")
font = prevfont
else if (fontok[code] == "")
print msg "unknown font `" code "'"
else {
prevfont = font
font = code
}
next
}
/^\.br/ {
print dobreak, "flush"
next
}
/^\.ds/ {
# note, macro-set-specific code often looks at .ds as well
if ($3 !~ /^"/)
strings[$2] = $3
else
strings[$2] = substr($0, index($0, "\"")+1)
next
}
/^\.ns/ {
print nobreak, "nospace"
next
}
/^\.rs/ {
print nobreak, "yesspace"
next
}
/^\.ad/ {
print nobreak, "both"
next
}
/^\.na/ {
print nobreak, "left"
next
}
/^\.nf/ {
fill = 0
print dobreak, "flush"
next
}
/^\.fi/ {
fill = 1
print dobreak, "flush"
next
}
/^\.\^x/ { # direct errors to this file: .^x filename
print nobreak, "errsto", $2
next
}
/^\.\^c/ { # define character: .^c name width text
if ($4 ~ /^"/)
s = substr($0, index($0, "\"")+1)
else
s = $4
ns = ""
while ((n = index(s, "\\")) > 0) {
if (n > 1)
ns = ns substr(s, 1, n-1)
n++
c = substr(s, n, 1)
if (c == "\\")
ns = ns "\\"
else if (c == "b")
ns = ns "\b"
s = substr(s, n+1)
}
ns = ns s
if ($2 == "hy") {
hyphens[font] = ns
hyphenwidths[font] = $3
} else {
chars[$2] = ns
charwidths[$2] = $3
}
next
}
/^\.\^f/ { # this font is okay: .^f fontname
# someday, this might take font-change codes as further arguments
fontok[$2] = "yes"
next
}
/^\.tm/ {
print msg $0
next
}
/^\.ps/ {
# ignore
next
}
/^\.ce/ {
if (NF > 1)
centering = $2
else
centering = 1
next
}
/^\.bp/ {
print dobreak, "need", 999
next
}
/^\.\^d/ { # debug control: .^d debugvar value
debug[$2] = $3
next
}
/^\.\^#/ { # set line number of next line: .^# no file
il = $2 - 1
lockil = 0
inname = $3
next
}
/^\.\^=/ { # lock line number to value: .^= no file
il = $2
lockil = 1
inname = $3
next
}
/^\.\\"/ { # comment
next
}
/^\./ {
print msg "command `" $1 "' unsupported or unknown"
}
END {
print dobreak, "need", 999 # flush page
}
+33
View File
@@ -0,0 +1,33 @@
/^\.\^b/ { # initialization
print nobreak, "fph", 1
next
}
/^[^.]/ { # text line -- reached only for input traps
if (afternext ~ /,fP/)
font = prevfont
if (afternext ~ /,tP/)
print dobreak, "toindent"
afternext = ""
next
}
/^\.ds/ { # to catch special strings
if ($3 !~ /^"/)
v = $3
else
v = substr($0, index($0, "\"")+1)
if ($2 ~ /^[LCR][HF]$/)
print nobreak, $2, v
# fallthrough to normal .ds processing in macro-independent stuff
}
/^\.lF/ {
# special footer fiddling
if (strings["by"] != "" && strings["nb"] != "")
lf = strings["by"] "; " strings["nb"]
else
lf = strings["by"] strings["nb"]
print nobreak, "LF", lf
next
}
/^\.\^e/ { # finalization
next
}
+40
View File
@@ -0,0 +1,40 @@
/^\.\^b/ { # initialization
nhnos[1] = 0
next
}
/^[^.]/ { # text line -- reached only for input traps
if (afternext == ",tP")
print dobreak, "toindent"
afternext = ""
next
}
/^\.nH/ { # fooling around for numbered headings
no = 1
if (NF > 1)
no = $2
if (no == 0) {
nhnos[1] = 0
no = 1
}
nhnos[no]++
for (n in nhnos)
if (n > no)
nhnos[n] = 0
s = ""
for (n = 1; n <= no; n++)
s = s nhnos[n] "."
strings["Nh"] = s # result in string for macro to grab
next
}
/^\.ds/ { # to catch special strings
if ($3 !~ /^"/)
v = $3
else
v = substr($0, index($0, "\"")+1)
if ($2 ~ /^[LCR][HF]$/)
print nobreak, $2, v
# fallthrough to normal .ds processing in macro-independent stuff
}
/^\.\^e/ { # finalization
next
}
+332
View File
@@ -0,0 +1,332 @@
# third pass: setting lines and pages
# The input language of this pass is basically <width, word> pairs, where
# "word" may have imbedded strangeness (backspaces, etc.) for font changes
# and special characters. Zero width is not special. A third field may
# appear to indicate that this is a fragment of a word that can be
# hyphenated; the third field is the width of the hyphen that would have
# to be added if the line broke after this fragment.
# Negative widths denote special operations. -3 is an error message, the
# second field being the message. -1 and -2 are control messages to this
# pass, the difference being whether a break is implied or not. The second
# field is a message type string; more fields may appear as arguments. The
# semantics of control messages are often -- but not always! -- similar to
# those of troff commands. For example, "linelen" is .ll, but "center" is
# not semantically equivalent to .ce -- it is related but more primitive.
BEGIN {
# input and output details
FS = "\t"
nobreak = -1
dobreak = -2
message = -3
errs = "awf.errs" # default only, normally changed by "errsto"
# page setup -- some are defaults only, normally altered by pass 2
nextlineno = 1
thispageno = 1
topmargin = 5
botmargin = 5
ind = 0 # current indent
tmpind = 0
pageoffset = "" # string to emit at start of each line
nospacemode = 1
hdrs["CH"] = "- % -"
nop = split("LH,CH,RH,LF,CF,RF", hdrnames, ",")
fph = 0 # print header on first page?
fill = 1
adj = "both"
pagelen = 66
linelen = 78
# line-builder setup
line = "" # line so far, without padding
paddable = "" # x means corresp. char in "line" is paddable
thislinelen = -1 # -1 means nothing there
cont = " " # thing to append to continue line
contlen = 1
eol = "" # thing to append to break line
eollen = 0
padfrom = "R" # "L" or "R", alternating for river avoidance
# many spaces, so we can use substr to get any number we need
sps = " "
sps = sps sps sps sps sps sps sps sps sps sps
}
{
# process word, if any, causing a break if appropriate
if ($1 >= 0 && thislinelen < 0) { # word, and first on line
line = $2
paddable = substr(sps, 1, length($2))
thislinelen = $1
} else if ($1 >= 0 && thislinelen+contlen+$1+$3 <= linelen-ind-tmpind) {
# word, and it fits on line
line = line cont $2
if (cont == " ")
paddable = paddable "x"
else
paddable = paddable substr(sps, 1, length(cont))
paddable = paddable substr(sps, 1, length($2))
thislinelen += contlen + $1
} else if ($1 == nobreak || $1 == message)
nop = 0 # no attention (i.e. break) needed here
else if ($1 == dobreak && $2 == "need" && \
nextlineno + $3 < pagelen + 1 - botmargin)
nop = 0 # enough space is available, no action needed
else if ($1 == dobreak && $2 == "toindent" && \
ind + tmpind + thislinelen < ind) {
# move to indent position within line; there is room
n = ind - (ind + tmpind + thislinelen)
line = line substr(sps, 1, n)
# nothing before this is paddable
paddable = substr(sps, 1, length(line))
thislinelen += n
# prevent padding immediately after this point
cont = ""
contlen = 0
} else if (thislinelen >= 0 || ($1 == dobreak && $2 == "need")) {
# must emit output, either due to break or "need"
# if at top of page, header
if (nextlineno == 1) {
for (i = int((topmargin-1)/2); i > 0; i--) {
print ""
nextlineno++
}
for (hno in hdrnames) {
h = hdrnames[hno]
if (hdrs[h] ~ /%/) {
n = split(hdrs[h], t, "%")
thispagehdrs[h] = t[1] thispageno t[2]
} else
thispagehdrs[h] = hdrs[h]
}
if (fph || thispageno > 1) {
lh = thispagehdrs["LH"]
ch = thispagehdrs["CH"]
rh = thispagehdrs["RH"]
lsp = int((linelen - length(lh ch rh)) / 2)
rsp = linelen - length(lh ch rh) - lsp
print pageoffset lh substr(sps, 1, lsp) ch substr(sps, 1, rsp) rh
} else
print ""
nextlineno++
while (nextlineno <= topmargin) {
print ""
nextlineno++
}
}
# the current line
# first, add a trailing hyphen if any
line = line eol
paddable = paddable substr(sps, 1, length(eol))
thislinelen += eollen
# trim trailing spaces if any
while (line ~ / $/) {
line = substr(line, 1, length(line)-1)
paddable = substr(paddable, 1, length(line))
thislinelen--
}
# print it in a suitable way
if (line == "") # empty always prints as nothing
print ""
else if ($1 < 0 && $2 == "center") {
# center it
hsp = int((linelen - thislinelen) / 2)
if (hsp < 0)
hsp = 0
print pageoffset substr(sps, 1, ind+tmpind+hsp) line
} else if (adj == "left" || (adj == "both" && \
($1 < 0 || index(paddable, "x") == 0)))
# no right-margin adjustment (disabled, inappropriate
# (line ended by break), or impossible)
print pageoffset substr(sps, 1, ind+tmpind) line
else if (adj == "both") {
# hard case -- adjust right margin
# sanity check
if (length(paddable) != length(line)) # aieeeee
printf "awf: %f != %f!\n", length(paddable), \
length(line) >errs
# compute parameters
textlen = linelen - (ind+tmpind)
mustadd = textlen - thislinelen
npad = 0 # number of paddable spaces
for (tmp = paddable; (i = index(tmp, "x")) > 0; \
tmp = substr(tmp, i+1))
npad++
addatall = int(mustadd/npad) # all grow this much
spall = substr(sps, 1, addatall)
nmore = mustadd - addatall*npad # this many grow more
# build padded output text
out = substr(sps, 1, ind+tmpind)
padno = 0
while ((i = index(paddable, "x")) > 0) {
out = out substr(line, 1, i)
padno++
out = out spall
if (padfrom == "L") {
if (padno <= nmore)
out = out " "
} else {
if (padno > npad-nmore)
out = out " "
}
line = substr(line, i+1)
paddable = substr(paddable, i+1)
}
# print it, plus remnant not processed by loop
print pageoffset out line
# tidy up
if (padfrom == "L")
padfrom = "R"
else
padfrom = "L"
}
# tidy up after output line
nextlineno++
line = ""
paddable = ""
thislinelen = -1
tmpind = 0
nospacemode = 0
# if we broke from a "need", go to bottom of page
if ($1 == dobreak && $2 == "need")
while (nextlineno < pagelen + 1 - botmargin) {
print ""
nextlineno++
}
# footer, if at bottom of page
if (nextlineno >= pagelen + 1 - botmargin) {
for (i = int((botmargin-1)/2); i > 0; i--) {
print ""
nextlineno++
}
# header code prepared thispagehdrs
lf = thispagehdrs["LF"]
cf = thispagehdrs["CF"]
rf = thispagehdrs["RF"]
lsp = int((linelen - length(lf cf rf)) / 2)
rsp = linelen - length(lf cf rf) - lsp
print pageoffset lf substr(sps, 1, lsp) cf substr(sps, 1, rsp) rf
nextlineno++
while (nextlineno <= pagelen) {
print ""
nextlineno++
}
nextlineno = 1
thispageno++
# after page break, should not space unnecessarily,
# and should pad first line from right
nospacemode = 1
padfrom = "R"
}
# we are finally done with emitting output
# pick up input word, if any
if ($1 >= 0) {
line = $2
paddable = substr(sps, 1, length($2))
thislinelen = $1
}
}
# if we broke, next line should pad from right
if ($1 == dobreak)
padfrom = "R"
# cleanup and post-break command processing
if ($1 >= 0 || $2 == "nohyphen") {
# reset hyphenation trickery after each word (fragment)
cont = " "
contlen = 1
eol = ""
eollen = 0
} else if ($2 == "need" || $2 == "toindent")
nop = 0 # dealt with above
else if ($2 == "flush" || $2 == "center")
nop = 0 # exist only to cause break
else if ($1 == message)
print "awf: " $2 >errs
else if ($2 == "gap") {
# gap between last word and next one should be >= $3
if (thislinelen >= 0) {
line = line substr(sps, 1, $3-1)
paddable = paddable substr(sps, 1, $3-1)
thislinelen += $3-1
}
} else if ($2 == "tabto") {
# move to tab stop at $3
if (thislinelen < 0)
thislinelen = 0 # make line exist
n = $3 - thislinelen
if (n > 0) { # must emit some space
line = line substr(sps, 1, n)
# nothing before a tab is paddable
paddable = substr(sps, 1, length(line))
thislinelen += n
# suppress space following
cont = ""
contlen = 0
}
} else if ($2 == "errsto")
errs = $3
else if ($2 ~ /^[LCR][HF]$/)
hdrs[$2] = $3
else if ($2 == "fph")
fph = $3
else if ($2 == "space") {
if (!nospacemode) {
# generate an empty line, which will be flushed by
# the next word; NB we know "space" caused a flush
line = ""
paddable = ""
thislinelen = linelen + 1
nospacemode = 0
}
} else if ($2 == "left")
adj = "left"
else if ($2 == "both")
adj = "both"
else if ($2 == "indent")
ind = $3
else if ($2 == "tempindent")
tmpind = $3
else if ($2 == "linelen")
linelen = $3
else if ($2 == "pagelen")
pagelen = $3
else if ($2 == "nospace")
nospacemode = 1
else if ($2 == "yesspace")
nospacemode = 0
else if ($2 == "hyphen") {
# discretionary hyphen at this point
cont = ""
contlen = 0
eol = $3
eollen = $4
} else if ($2 == "userhyphen") {
# user-supplied hyphen at this point
cont = $3
contlen = $4
eol = $3
eollen = $4
} else if ($2 == "pageoffset")
pageoffset = substr(sps, 1, $3)
else
print "awf: URK -- INTERNAL OPCODE `" $2 "' UNKNOWN" >errs
}
END {
# second pass is supposed to fake a .ne to flush the last page
if (nextlineno != 1)
print "awf: last page not flushed!" >errs
}
+4
View File
@@ -0,0 +1,4 @@
@echo off
echo ---------- %1 ----------
cd %1
nmake /f makefile.vc /nologo %2
+5
View File
@@ -0,0 +1,5 @@
*.log
*.log.*
*.pix
*.pix.*
.cvsignore
-106
View File
@@ -1,106 +0,0 @@
add_subdirectory(ref)
add_definitions(-DCONSOLE)
brlcad_addexec(pixcmp pixcmp.c libbu)
brlcad_add_test(
NAME bench_pixcmp_tolerance
COMMAND
${CMAKE_COMMAND} "-DPIXCMP=$<TARGET_FILE:pixcmp>" "-DTEST_DIR=${CMAKE_CURRENT_BINARY_DIR}"
-P "${CMAKE_CURRENT_SOURCE_DIR}/pixcmp_test.cmake"
)
set(BARK_SOURCES benchmark.c compute.c run.c clean.c)
brlcad_addexec(bark "${BARK_SOURCES}" "libbu;${M_LIBRARY}" NO_STRICT NO_INSTALL TEST_USESDATA)
if(BUILD_TESTING)
configure_file(run.sh "${CMAKE_CURRENT_BINARY_DIR}/benchmark" COPYONLY)
install(PROGRAMS "${CMAKE_CURRENT_BINARY_DIR}/benchmark" DESTINATION ${BIN_DIR})
endif(BUILD_TESTING)
distclean("${CMAKE_CURRENT_BINARY_DIR}/benchmark")
if(BUILD_TESTING)
add_custom_command(
OUTPUT ${CMAKE_CURRENT_BINARY_DIR}/benchmark-done
COMMAND "${CMAKE_COMMAND}" -E copy_if_different ${CMAKE_CURRENT_SOURCE_DIR}/run.sh $<TARGET_FILE_DIR:bark>/benchmark
COMMAND "${CMAKE_COMMAND}" -E touch ${CMAKE_CURRENT_BINARY_DIR}/benchmark-done
DEPENDS ${CMAKE_CURRENT_SOURCE_DIR}/run.sh
)
add_custom_target(benchmark_cp ALL DEPENDS ${CMAKE_CURRENT_BINARY_DIR}/benchmark-done)
set_target_properties(benchmark_cp PROPERTIES FOLDER "Benchmark")
endif(BUILD_TESTING)
distclean(${CMAKE_BINARY_DIR}/${BIN_DIR}/benchmark)
file(WRITE "${CMAKE_BINARY_DIR}/CMakeTmp/benchmsg.cmake" "message(\"---\")\n")
file(
APPEND
"${CMAKE_BINARY_DIR}/CMakeTmp/benchmsg.cmake"
"message(\"Run 'make benchmark-clean' in the bench directory to delete the logic\")\n"
)
file(
APPEND
"${CMAKE_BINARY_DIR}/CMakeTmp/benchmsg.cmake"
"message(\"and image files generated during the benchmark analysis.\")\n"
)
cmakefiles(
CMakeLists.txt
pixcmp_test.cmake
run.sh
try.sh
viewdiff.sh
)
if(SH_EXEC AND TARGET m35.g AND BUILD_TESTING)
# CTest enabled short run of the benchmark suite
brlcad_add_test(NAME benchmark COMMAND ${SH_EXEC} "$<TARGET_FILE_DIR:bark>/benchmark" run TIMEFRAME=1)
set_tests_properties(benchmark PROPERTIES LABELS "Benchmark")
add_custom_target(
benchmark-check
COMMAND ${CMAKE_CTEST_COMMAND} -L Benchmark --output-on-failure
DEPENDS rt pixcmp BENCHMARK_PIX_cp PIX_LOG_cp benchmark_cp
)
add_dependencies(
benchmark-check
bldg391.g
m35.g
moss.g
sphflake.g
star.g
world.g
)
set_target_properties(benchmark-check PROPERTIES FOLDER "Benchmark")
if(TARGET check)
add_dependencies(check benchmark-check)
endif(TARGET check)
# Full run of the benchmark suite
add_custom_target(
benchmark
COMMAND ${SH_EXEC} $<TARGET_FILE_DIR:bark>/benchmark run
COMMAND ${CMAKE_COMMAND} -P "${CMAKE_BINARY_DIR}/CMakeTmp/benchmsg.cmake"
DEPENDS rt pixcmp BENCHMARK_PIX_cp PIX_LOG_cp benchmark_cp
)
add_dependencies(
benchmark
bldg391.g
m35.g
moss.g
sphflake.g
star.g
world.g
)
set_target_properties(benchmark PROPERTIES FOLDER "Benchmark")
# benchmark cleanup targets
add_custom_target(benchmark-clean ${SH_EXEC} ${CMAKE_BINARY_DIR}/bin/benchmark clean)
set_target_properties(benchmark-clean PROPERTIES FOLDER "Benchmark")
add_custom_target(benchmark-clobber ${SH_EXEC} ${CMAKE_BINARY_DIR}/bin/benchmark clobber)
set_target_properties(benchmark-clobber PROPERTIES FOLDER "Benchmark")
endif(SH_EXEC AND TARGET m35.g AND BUILD_TESTING)
# Local Variables:
# tab-width: 8
# mode: cmake
# indent-tabs-mode: t
# End:
# ex: shiftwidth=2 tabstop=8
+39
View File
@@ -0,0 +1,39 @@
/*
* bench/Cakefile
*/
#define SRCDIR bench
#define PRODUCTS pixcmp
#define SRCSUFF .c
/* #define MANSECTION 9 */
#define FILES pixcmp
#include "../Cakefile.defs"
#ifdef NFS
/* Pick up any shell scripts needed */
%.sh: if exist ../SRCDIR/%.sh
rm -f %.sh
ln ../SRCDIR/%.sh %.sh
#endif
#include "../Cakefile.prog"
clobber&: xxclober
@echo "About to wipe out all pictures and binary files in this directory"
@echo "Send SIGINT (typ. ^C) within 3 seconds to abort"
@sleep 3
rm -f *.log.* *.pix.* # old versions
rm -f *.log *.pix # last try
#define clobber xxclober /* rename "clobber" in Cakefile.rules */
clean&:
@echo "Removing object files and pixcmp"
rm -f *.o pixcmp
pixcmp: OBJ
CC LDFLAGS -o pixcmp OBJ
#include "../Cakefile.rules"
-953
View File
@@ -1,953 +0,0 @@
/* B E N C H M A R K . C
* BRL-CAD
*
* Copyright (c) 2011-2026 United States Government as represented by
* the U.S. Army Research Laboratory.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above
* copyright notice, this list of conditions and the following
* disclaimer in the documentation and/or other materials provided
* with the distribution.
*
* 3. The name of the author may not be used to endorse or promote
* products derived from this software without specific prior written
* permission.
*
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS
* OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
* DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE
* GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
* NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
/** @file benchmark.c
*
* This is the BRL-CAD Benchmark.
*
* The benchmark suite will test the performance of a system by
* iteratively rendering several well-known datasets into 512x512
* images where performance metrics are documented and fairly well
* understood. The local machine's performance is compared to the
* base system (called VGR) and a numeric "VGR" multiplier of
* performance is computed. This number is a simplified metric from
* which one may qualitatively compare cpu and cache performance,
* versions of BRL-CAD, and different compiler characteristics.
*
*/
#include "common.h"
#include <stdlib.h>
#include <string.h>
#include <time.h>
#include <sys/stat.h>
/* TODO - fall back on https://github.com/sandsmark/winuname for Windows? */
#ifdef HAVE_SYS_UTSNAME_H
# include <sys/utsname.h>
#endif
#include "bio.h"
#include "bu.h"
/* TODO: !!! probably will need variants of these */
int bu_exec(const char *program, void *data, struct bu_vls *out, struct bu_vls *err) {if (!program || !out || !err || !data) return 1; return 0;}
int bu_grep(const char *pattern, const char *input, int(*callback)(const char *line, void *data), void *data) {if (!pattern || !input || !data) return 1; if (!callback) bu_log("TODO: need default callback!!!\n"); return 0;}
int bu_file_glob(const char *pattern, char **paths) {if (!pattern || !paths) return 1; return 0;}
const char *format_elapsed(double elapsed) {if (elapsed > 0) return "0 1 2"; return "-0 -1 -2";}
int perf(const struct bu_vls *vp, const char *items, const char *args[]) {if (!vp || !items || !args) return -1; return 0;}
double calculate_vgr(const struct bu_vls *summary) {if (!summary) return -0.0; return 0.0;}
extern int bench(const char *cmd);
/**
* this routine writes the provided argument(s) to a log file as well
* as echoing them to stdout if we're not in quiet mode.
*/
static void
record(const char *fmt, ...)
{
struct bu_vls str = BU_VLS_INIT_ZERO;
va_list ap;
const char *LOGFILE = getenv("LOGFILE");
const char *QUIET = getenv("QUIET");
if (!fmt) {
return;
}
va_start(ap, fmt);
bu_vls_vprintf(&str, fmt, ap);
va_end(ap);
if (!BU_STR_EQUAL(LOGFILE, "")) {
FILE *fp = fopen(LOGFILE, "a");
fprintf(fp, "%s", bu_vls_addr(&str));
fclose(fp);
}
if (bu_str_false(QUIET)) {
bu_log("%s", bu_vls_addr(&str));
}
bu_vls_free(&str);
}
static void
display(const char *fmt, ...)
{
struct bu_vls str = BU_VLS_INIT_ZERO;
va_list ap;
if (!fmt) {
return;
}
va_start(ap, fmt);
bu_vls_vprintf(&str, fmt, ap);
va_end(ap);
bu_log("%s", bu_vls_cstr(&str));
bu_vls_free(&str);
}
static void
sink(const char *fmt, ...)
{
if (!fmt) {
return;
}
}
/************************
* search for resources *
************************/
typedef enum {
executable=0x1,
file=0x2,
directory=0x4,
script=0x8
} look_for_type_t;
#define TYPE2STR(_t) \
((_t) == executable) ? "executable" : \
((_t) == file) ? "file" : \
((_t) == directory) ? "directory" : \
((_t) == script) ? "script" : \
"unknown"
static void
look_for(void (*verbose)(const char *, ...), look_for_type_t type, const char *label, const char *var, const char*paths[])
{
char *val;
/* utility function to search for a certain filesystem object in a
* list of paths.
*/
if (!var || !paths) {
return;
}
if (!verbose) {
verbose = sink;
}
verbose("Looking for %s\n", label);
/* get the value of the variable */
val = getenv(var);
if (val && (strlen(val) > 0)) {
if (label) {
verbose("...using %s from %s variable setting\n", val, var);
}
} else {
while (paths && *paths) {
int failed=0;
switch (type) {
default:
case directory:
/* should work without read bit */
if (!bu_file_directory(*paths)) {
failed=1;
}
/* fall through */
case executable:
case script:
if (!bu_file_executable(*paths)) {
failed=1;
}
break;
case file:
if (!bu_file_exists(*paths, NULL)) {
failed=1;
}
break;
}
if (!failed) {
verbose("...found %s %s\n", TYPE2STR(type), *paths);
bu_setenv(var, *paths, 1);
break;
}
paths++;
}
}
}
static void
set_if_unset(void (*echo)(const char *, ...), void (*verbose)(const char *, ...), const char *var, const char *val)
{
if (!var || !val) {
return;
}
const char *setval = getenv(var);
if (!echo) {
echo = sink;
}
if (!verbose) {
verbose = sink;
}
if (!setval || (strlen(setval) == 0)) {
verbose("%s=\"%s\"\n", var, val);
bu_setenv(var, val, 1);
}
setval = getenv(var);
echo("Using [%s] for %s\n", setval ? setval : "", var);
}
/* callback to bu_grep() */
static int
stashline(const char *line, void *data)
{
struct bu_vls *vls = (struct bu_vls *)data;
BU_CK_VLS(vls);
bu_vls_printf(vls, "%s\n", line);
return 0;
}
int
main(int ac, char *av[])
{
int arg;
struct bu_vls rtargs = BU_VLS_INIT_ZERO;
struct bu_vls str = BU_VLS_INIT_ZERO;
const char *RT = NULL;
const char *DB = NULL;
const char *PIX = NULL;
const char *LOG = NULL;
const char *CMP = NULL;
const char *ELP = NULL;
char root[MAXPATHLEN] = {0};
char db[MAXPATHLEN] = {0};
char pix[MAXPATHLEN] = {0};
char thisp[MAXPATHLEN] = {0};
char *argv[MAXPATHLEN] = {NULL};
struct bu_vls vp = BU_VLS_INIT_ZERO;
long MAXTIME = 0;
long TIMEFRAME = 0;
int64_t start = 0;
int ret = 0;
void (*verbose_echo)(const char *, ...) = sink;
void (*echo)(const char *, ...) = record;
bu_setprogname(av[0]);
/* process the argument list for commands */
for (arg=1; arg<ac; arg++) {
if (BU_STR_EQUAL(av[arg], "clean")) {
bu_setenv("CLEAN", "1", 1);
continue;
}
if (BU_STR_EQUAL(av[arg], "clobber")) {
bu_setenv("CLEAN", "1", 1);
bu_setenv("CLOBBER", "1", 1);
continue;
}
if (BU_STR_EQUAL(av[arg], "h")) {
bu_setenv("HELP", "1", 1);
continue;
}
if (BU_STR_EQUAL(av[arg], "help")) {
bu_setenv("HELP", "1", 1);
continue;
}
if (bu_strncasecmp(av[arg], "instruct", 8)) {
bu_setenv("INSTRUCTIONS", "1", 1);
continue;
}
if (BU_STR_EQUAL(av[arg], "start")) {
continue;
}
if (BU_STR_EQUAL(av[arg], "quiet")) {
bu_setenv("QUIET", "1", 1);
continue;
}
if (BU_STR_EQUAL(av[arg], "verbose")) {
bu_setenv("VERBOSE", "1", 1);
continue;
}
if (BU_STR_EQUAL(av[arg], "run")) {
bu_setenv("RUN", "1", 1);
continue;
}
if (strchr(av[arg], '=')) {
/* TODO: !!! make sure this still works */
char *var = bu_strdup(av[arg]);
char *val = strtok(var, "=");
if (var && val) {
bu_setenv(var, val, 1);
}
bu_free(var, "strdup av[arg]");
continue;
}
bu_log("WARNING: Passing unknown option [%s] to RT\n", av[arg]);
bu_vls_printf(&rtargs, " %s", av[arg]);
}
/***
* handle help before main processing
***/
if (bu_str_true(getenv("HELP"))) {
bu_log("Usage: %s [command(s)] [OPTION=value] [RT_OPTIONS]\n", av[0]);
bu_log("\n");
bu_log("Available commands:\n");
bu_log(" clean\n");
bu_log(" clobber\n");
bu_log(" help (this is what you are reading right now)\n");
bu_log(" instructions\n");
bu_log(" quiet\n");
bu_log(" verbose\n");
bu_log(" run (this is probably what you want)\n");
bu_log("\n");
bu_log("Available options:\n");
bu_log(" RT=/path/to/rt_binary (e.g., rt)\n");
bu_log(" DB=/path/to/reference/geometry (e.g. ../db)\n");
bu_log(" PIX=/path/to/reference/images (e.g., ../pix)\n");
bu_log(" LOG=/path/to/reference/logs (e.g., ../pix)\n");
bu_log(" CMP=/path/to/pixcmp_tool (e.g., pixcmp)\n");
bu_log(" ELP=/path/to/time_tool (e.g., elapsed.sh)\n");
bu_log(" TIMEFRAME=#seconds (default 32)\n");
bu_log(" MAXTIME=#seconds (default 300)\n");
bu_log(" DEVIATION=%%deviation (default 3)\n");
bu_log(" AVERAGE=#frames (default 3)\n");
bu_log("\n");
bu_log("Available RT options:\n");
bu_log(" -P# (e.g., -P1 to force single CPU)\n");
bu_log(" See the 'rt' manpage for additional options\n");
bu_log("\n");
bu_log("The BRL-CAD Benchmark tests the overall performance of a system\n");
bu_log("compared to a stable well-known baseline. The Benchmark calculates a\n");
bu_log("figure-of-merit for this system that may be directly compared to other\n");
bu_log("Benchmark runs on other system configurations.\n");
bu_log("\n");
bu_log("BRL-CAD is a powerful cross-platform open source solid modeling system.\n");
bu_log("For more information about BRL-CAD, see http://brlcad.org\n");
bu_log("\n");
bu_log("Run '%s instructions' or see the manpage for additional information.\n", av[0]);
bu_exit(1, NULL);
}
/***
* handle instructions before main processing
***/
if (bu_str_true(getenv("INSTRUCTIONS"))) {
bu_log("\n");
bu_log("This program runs the BRL-CAD Benchmark. The benchmark suite will\n");
bu_log("test the performance of a system by iteratively rendering several\n");
bu_log("well-known datasets into 512x512 images where performance metrics are\n");
bu_log("documented and fairly well understood. The local machine's\n");
bu_log("performance is compared to the base system (called VGR) and a numeric\n");
bu_log("\"VGR\" multiplier of performance is computed. This number is a\n");
bu_log("simplified metric from which one may qualitatively compare cpu and\n");
bu_log("cache performance, versions of BRL-CAD, and different compiler\n");
bu_log("characteristics.\n");
bu_log("\n");
bu_log("The suite is intended to be run from a source distribution of BRL-CAD\n");
bu_log("after the package has been compiled either directly or via a make\n");
bu_log("build system target. There are, however, several environment\n");
bu_log("variables that will modify how the BRL-CAD benchmark behaves so that\n");
bu_log("it may be run in a stand-alone environment:\n");
bu_log("\n");
bu_log(" RT - the rt binary (e.g. ../src/rt/rt or /usr/brlcad/bin/rt)\n");
bu_log(" DB - the directory containing the reference geometry (e.g. ../db)\n");
bu_log(" PIX - the directory containing the reference images (e.g. ../pix)\n");
bu_log(" LOG - the directory containing the reference logs (e.g. ../pix)\n");
bu_log(" CMP - the name of a pixcmp tool (e.g. ./pixcmp or cmp)\n");
bu_log(" ELP - the name of an elapsed time tool (e.g. ../sh/elapsed.sh)\n");
bu_log(" TIMEFRAME - the minimum number of seconds each trace needs to take\n");
bu_log(" MAXTIME - the maximum number of seconds to spend on any test\n");
bu_log(" DEVIATION - the minimum sufficient %% deviation from the average\n");
bu_log(" AVERAGE - how many frames to average together\n");
bu_log(" VERBOSE - turn on extra debug output for testing/development\n");
bu_log(" QUIET - turn off all printing output (writes results to summary)\n");
bu_log(" INSTRUCTIONS - display detailed instructions\n");
bu_log(" RUN - start a benchmark analysis\n");
bu_log("\n");
bu_log("The TIMEFRAME, MAXTIME, DEVIATION, and AVERAGE options control how the\n");
bu_log("benchmark will proceed including how long it should take. Each\n");
bu_log("individual benchmark run will consume at least a minimum TIMEFRAME of\n");
bu_log("wallclock time so that the results can stabilize. After consuming at\n");
bu_log("least the minimum TIMEFRAME, additional frames may be computed until\n");
bu_log("the standard deviation from the last AVERAGE count of frames is below\n");
bu_log("the specified DEVIATION. When a test is run and it completes in less\n");
bu_log("than TIMEFRAME, the raytrace is restarted using double the number of\n");
bu_log("rays from the previous run. If the machine is fast enough, the\n");
bu_log("benchmark may accelerate the number or rays being fired. These\n");
bu_log("additional rays are hypersampled but without any jitter, so it's\n");
bu_log("effectively performing a multiplier amount of work over the initial\n");
bu_log("frame.\n");
bu_log("\n");
bu_log("Please send your BRL-CAD Benchmark results to the developers along with\n");
bu_log("detailed system information to <devs@brlcad.org>. Include at least:\n");
bu_log("\n");
bu_log(" 0) Compiler name and version (e.g. gcc --version)\n");
bu_log(" 1) All generated log files (i.e. *.log* after benchmark completes)\n");
bu_log(" 2) Anything else you think might be relevant to performance\n");
bu_log("\n");
bu_log("The manual page has even more information and specific usage examples.\n");
bu_log("Run 'brlman benchmark'.\n");
bu_log("\n");
bu_exit(0, NULL);
}
/***
* handle clean/clobber before main processing
***/
if (bu_str_true(getenv("CLEAN"))) {
size_t i;
size_t cnt;
size_t num;
char cwd[MAXPATHLEN] = {0};
const char *tests[] = {"moss", "world", "star", "bldg391", "m35", "sphflake", NULL};
char **paths = NULL;
int printed = 0;
bu_log("\n");
if (bu_str_true(getenv("CLOBBER"))) {
bu_log("About to wipe out all benchmark images and log files in %s\n", bu_getcwd(cwd, MAXPATHLEN));
bu_log("Send SIGINT (type ^C) within 5 seconds to abort\n");
sleep(5);
} else {
bu_log("Deleting most benchmark images and log files in %s\n", bu_getcwd(cwd, MAXPATHLEN));
bu_log("Running '%s clobber' will remove run logs.\n", av[0]);
}
bu_log("\n");
for (i=0; tests[i]; i++) {
struct bu_vls pattern_str = BU_VLS_INIT_ZERO;
char *pattern[5] = {NULL, NULL, NULL, NULL, NULL};
size_t j;
/* rm -f $i.log $i.pix $i-[0-9]*.log $i-[0-9]*.pix */
bu_vls_printf(&pattern_str, "%s.log %s.pix %s-[0-9]*.log %s-[0-9]*.pix", tests[i], tests[i], tests[i], tests[i]);
bu_log("rm -f %s\n", bu_vls_cstr(&pattern_str));
j = bu_argv_from_string(pattern, 4, bu_vls_addr(&pattern_str));
while (j > 0) {
num = bu_file_glob(pattern[j-1], paths);
if (!num || !paths || !paths[0]) {
j--;
continue;
}
cnt = num;
while (num > 0) {
bu_file_delete(paths[num-1]);
num--;
}
bu_argv_free(cnt, paths);
paths = NULL;
j--;
}
bu_vls_free(&pattern_str);
}
if (bu_str_true(getenv("CLOBBER"))) {
/* NEVER automatically delete the summary file, but go
* ahead with the rest.
*/
num = bu_file_glob("benchmark-[0-9]*-run.log", paths);
cnt = num;
while (num > 0) {
if (paths) {
bu_log("rm -f %s\n", paths[num-1]);
bu_file_delete(paths[num-1]);
}
num--;
}
bu_argv_free(cnt, paths);
paths = NULL;
}
if (bu_file_exists("summary", NULL)) {
if (!printed) {
bu_log("\nThe following files must be removed manually:\n");
printed=1;
}
bu_log("summary ");
}
num = bu_file_glob("benchmark-[0-9]*-run.log", paths);
cnt = num;
while (num > 0) {
if (!printed) {
bu_log("\nThe following files must be removed manually:\n");
printed=1;
}
if (paths)
bu_log("%s ", paths[num-1]);
num--;
}
bu_argv_free(cnt, paths);
paths = NULL;
if (printed) {
bu_log("\n");
}
if (bu_str_true(getenv("CLOBBER"))) {
bu_log("\nBenchmark clobber complete.\n");
} else {
bu_log("\nBenchmark clean complete.\n");
}
bu_exit(0, NULL);
}
/***
* B E G I N
***/
if (bu_str_false(getenv("RUN"))) {
bu_exit(1, "Type '%s help' for usage.\n", av[0]);
}
/* where to write results */
{
int fd;
const char *logfile;
bu_vls_printf(&str, "run-%d-benchmark.log", bu_pid());
logfile = bu_vls_addr(&str);
bu_setenv("LOGFILE", logfile, 1);
fd = open(logfile, O_WRONLY|O_CREAT, S_IRUSR | S_IWUSR);
if (fd < 0 || !bu_file_writable(logfile)) {
if (!BU_STR_EQUAL(logfile, "/dev/null")) {
bu_log("ERROR: Unable to log to %s\n", logfile);
}
/* FIXME: not valid logfile on windows, use 'nul' */
bu_setenv("LOGFILE", "/dev/null", 1);
}
}
if (bu_str_true(getenv("QUIET"))) {
if (bu_str_true(getenv("VERBOSE"))) {
bu_log("Verbose output quelled by quiet option. Further output disabled.\n");
}
} else {
if (bu_str_true(getenv("VERBOSE"))) {
verbose_echo=display;
bu_log("Verbose output enabled\n");
}
}
{
struct bu_vls v = BU_VLS_INIT_ZERO;
char rfc2822[1024] = {0};
const char *logfile = getenv("LOGFILE");
#ifdef HAVE_SYS_UTSNAME_H
struct utsname n;
time_t t = time(NULL);
strftime(rfc2822, sizeof(rfc2822), "%a, %d %b %Y %H:%M:%S %Z", localtime(&t));
if (uname(&n) == 0) {
bu_vls_printf(&v, "%s %s %s %s %s", n.sysname, n.nodename, n.release, n.version, n.machine);
} else {
bu_vls_strcat(&v, "unknown");
}
#endif
echo("B R L - C A D B E N C H M A R K\n");
echo("=================================\n");
echo("Running %s on %s\n", av[0], rfc2822);
echo("Logging output to %s\n", logfile ? logfile : "disabled");
echo("%s\n\n", bu_vls_addr(&v));
}
bu_dir(root, MAXPATHLEN, BU_DIR_BIN, NULL);
bu_dir(db, MAXPATHLEN, BU_DIR_DATA, "db", NULL);
bu_dir(pix, MAXPATHLEN, BU_DIR_DATA, "pix" , NULL);
bu_dir(thisp, MAXPATHLEN, BU_DIR_CURR, NULL);
bu_vls_printf(&vp,
"%s/rt "
"%s/rt "
"./rt",
root, thisp);
bu_argv_from_string(argv, 32, bu_vls_addr(&vp));
look_for(verbose_echo, executable, "the BRL-CAD raytracer", "RT", (const char **)argv);
bu_vls_trunc(&vp, 0);
bu_vls_printf(&vp,
"%s/moss.g "
"%s/db/moss.g "
"%s/../db/moss.g "
"./db/moss.g "
"./moss.g",
db, thisp, thisp);
bu_argv_from_string(argv, 32, bu_vls_addr(&vp));
look_for(verbose_echo, file, "a benchmark geometry directory", "DB", (const char **)argv);
bu_vls_trunc(&vp, 0);
if (getenv("DB") && !bu_file_directory(getenv("DB"))) {
bu_setenv("DB", bu_path_dirname(getenv("DB")), 1);
}
bu_vls_printf(&vp,
"%s/moss.pix "
"%s/pix/moss.pix "
"%s/../pix/moss.pix "
"%s/../../pix/moss.pix "
"%s/../../../pix/moss.pix "
"./pix/moss.pix "
"./moss.pix",
pix, thisp, thisp, thisp, thisp);
bu_argv_from_string(argv, 32, bu_vls_addr(&vp));
look_for(verbose_echo, file, "a benchmark reference image directory", "PIX", (const char **)argv);
bu_vls_trunc(&vp, 0);
if (getenv("PIX") && !bu_file_directory(getenv("PIX"))) {
bu_setenv("PIX", bu_path_dirname(getenv("PIX")), 1);
}
const char *pix_env = getenv("PIX");
bu_vls_printf(&vp,
"%s "
"%s "
"%s/pix "
"%s/../pix "
"%s/../../pix "
"%s/../../../pix "
"./pix",
pix_env ? pix_env : "", pix, thisp, thisp, thisp, thisp);
bu_argv_from_string(argv, 32, bu_vls_addr(&vp));
look_for(verbose_echo, directory, "a benchmark reference log directory", "LOG", (const char **)argv);
bu_vls_trunc(&vp, 0);
bu_vls_printf(&vp,
"%s/pixcmp "
"%s/pixcmp "
"%s/bench/pixcmp "
"%s/../bench/pixcmp "
"./pixcmp",
root, thisp, thisp, thisp);
bu_argv_from_string(argv, 32, bu_vls_addr(&vp));
look_for(verbose_echo, executable, "a pixel comparison utility", "CMP", (const char **)argv);
bu_vls_trunc(&vp, 0);
/* FIXME: elapsed is no more */
bu_vls_printf(&vp,
"%s/elapsed.sh "
"%s/elapsed.sh "
"%s/sh/elapsed.sh "
"%s/../sh/elapsed.sh "
"%s/../../sh/elapsed.sh "
"%s/../../../sh/elapsed.sh "
"./elapsed.sh",
root, thisp, thisp, thisp, thisp, thisp);
bu_argv_from_string(argv, 32, bu_vls_addr(&vp));
look_for(verbose_echo, script, "a time elapsed utility", "ELP", (const char **)argv);
bu_vls_trunc(&vp, 0);
/*********************
* output parameters *
*********************/
/* sanity check, output all the final settings together */
RT = getenv("RT");
if (RT && strlen(RT) > 0) {
echo("Using [%s] for RT\n", RT);
} else {
bu_exit(1, "ERROR: Could not find the BRL-CAD raytracer\n");
}
DB = getenv("DB");
if (DB && strlen(DB) > 0) {
echo("Using [%s] for DB\n", DB);
} else {
bu_exit(1, "ERROR: Could not find the BRL-CAD database directory\n");
}
PIX = getenv("PIX");
if (PIX && strlen(PIX) > 0) {
echo("Using [%s] for PIX\n", PIX);
} else {
bu_exit(1, "ERROR: Could not find the BRL-CAD reference images\n");
}
LOG = getenv("LOG");
if (LOG && strlen(LOG) > 0) {
echo("Using [%s] for LOG\n", LOG);
} else {
bu_exit(1, "ERROR: Could not find the BRL-CAD reference logs\n");
}
CMP = getenv("CMP");
if (CMP && strlen(CMP) > 0) {
echo("Using [%s] for CMP\n", CMP);
} else {
bu_exit(1, "ERROR: Could not find the BRL-CAD pixel comparison utility\n");
}
ELP = getenv("ELP");
if (ELP && strlen(ELP) > 0) {
echo("Using [%s] for ELP\n", ELP);
} else {
bu_exit(1, "ERROR: Could not find the BRL-CAD time elapsed script\n");
}
/* determine the minimum time requirement in seconds for a single test run */
set_if_unset(echo, verbose_echo, "TIMEFRAME", "32");
/* approximate maximum time in seconds that a given test is allowed to take */
set_if_unset(echo, verbose_echo, "MAXTIME", "300");
{
char *mtimestr = getenv("MAXTIME");
MAXTIME = (mtimestr) ? strtol(mtimestr, NULL, 0) : 300;
char *timeframestr = getenv("TIMEFRAME");
TIMEFRAME = (timeframestr) ? strtol(timeframestr, NULL, 0) : 32;
if (MAXTIME < TIMEFRAME) {
bu_exit(1, "ERROR: MAXTIME must be greater or equal to TIMEFRAME\n");
}
}
/* maximum deviation percentage */
set_if_unset(echo, verbose_echo, "DEVIATION", "3");
/* maximum number of iterations to average */
set_if_unset(echo, verbose_echo, "AVERAGE", "3");
/* end of settings, separate the output */
echo("\n");
/**************************
* output run-time status *
**************************/
/* determine raytracer version */
echo("RT reports the following version information:\n");
{
struct bu_vls rtout = BU_VLS_INIT_ZERO;
struct bu_vls grep1 = BU_VLS_INIT_ZERO;
struct bu_vls grep2 = BU_VLS_INIT_ZERO;
RT = getenv("RT");
bu_exec(RT, NULL, &rtout, &rtout);
bu_grep("BRL-CAD", bu_vls_cstr(&rtout), stashline, (void *)&grep1);
bu_grep("Release", bu_vls_cstr(&grep1), stashline, (void *)&grep2);
if (bu_vls_strlen(&grep2) > 0) {
echo("%s\n", bu_vls_addr(&grep2));
} else {
echo("Unknown\n\n");
}
bu_vls_free(&grep2);
bu_vls_free(&grep1);
bu_vls_free(&rtout);
}
/* let the user know about how long this might take */
{
struct bu_vls elapsed = BU_VLS_INIT_ZERO;
double mintime = 6.0 * TIMEFRAME;
double maxtime = 6.0 * MAXTIME;
double estimate = 3.0 * mintime;
if (mintime < 1.0)
mintime = 0; /* zero is okay */
bu_vls_sprintf(&elapsed, "%s", format_elapsed(mintime));
echo("Minimum run time is %s\n", bu_vls_cstr(&elapsed));
if (maxtime < 1.0)
maxtime = 1.0; /* zero would be misleading */
bu_vls_sprintf(&elapsed, "%s", format_elapsed(maxtime));
echo("Maximum run time is %s\n", bu_vls_cstr(&elapsed));
if (estimate > maxtime)
estimate = maxtime;
echo("Estimated time is %s\n", format_elapsed(estimate));
}
/************************
* Run the actual tests *
************************/
start = bu_gettime();
echo("Running the BRL-CAD Benchmark tests... please wait ...\n\n");
ret += bench("moss");
ret += bench("world");
ret += bench("star");
ret += bench("bldg391");
ret += bench("m35");
ret += bench("sphflake");
echo("\n... Done.\n");
echo("Total testing time elapsed: %.2lfs\n", format_elapsed(bu_gettime() - start));
if (ret != 0) {
echo("\n");
echo("THE BENCHMARK ANALYSIS DID NOT COMPLETE SUCCESSFULLY.\n");
echo("\n");
echo("A benchmark failure means this is not a viable install of BRL-CAD. This may be\n");
echo("a new bug or (more likely) is a compilation configuration error. Ensure your\n");
echo("compiler has strict aliasing disabled, compilation is optimized, and you have\n");
echo("installed BRL-CAD (some platforms require this). If you still get a failure,\n");
echo("please report your configuration information to benchmark@brlcad.org\n");
echo("\n");
echo("Output was saved to %s from %s\n", LOG, bu_dir(NULL, 0, BU_DIR_CURR, NULL));
echo("Run '%s clean' to remove generated pix files.\n", av[0]);
echo("Benchmark testing failed.\n");
return 2;
}
/******************************
* compute and output results *
******************************/
{
struct bu_vls performance = BU_VLS_INIT_ZERO;
ret = perf(&performance, /*...!!!...*/"moss world star bldg391 m35 sphflake", (const char **)argv);
if (ret == 0) {
/* !!! write performance to summary */
}
echo("\n");
echo("The following files have been generated and/or modified:\n");
echo(" *.log ..... final log files for each individual raytrace test\n");
echo(" *.pix ..... final pix image files for each individual raytrace test\n");
echo(" *.log.* ... log files for previous frames and raytrace tests\n");
echo(" *.pix.* ... pix image files for previous frames and raytrace tests\n");
echo(" summary ... performance results summary, 2 lines per run\n");
echo("\n");
echo("Run '%s clean' to remove generated pix files.\n", av[0]);
echo("\n");
echo("Summary:\n");
echo("%s\n", bu_vls_cstr(&performance));
{
double vgr = calculate_vgr(&performance);
if (vgr > 0.0) {
echo("\n");
echo("#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#\n");
echo("Benchmark results indicate an approximate VGR performance metric of %ld\n", (long int)vgr);
echo("Logarithmic VGR metric is %.2lf (natural logarithm is %.2lf)\n", log10(vgr), log(vgr));
echo("#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#\n");
echo("\n");
echo("These numbers seem to indicate that this machine is approximately %ld times", (long int)vgr);
echo("faster than the reference machine being used for comparison, a VAX 11/780\n");
echo("running 4.3 BSD named VGR. These results are in fact approximately %.2lf", log10(vgr));
echo("orders of magnitude faster than the reference.\n");
echo("\n");
echo("Here are some other approximated VGR results for perspective:\n");
echo(" 120 on a 200MHz R5000 running IRIX 6.5\n");
echo(" 250 on a 500 MHz Pentium III running RedHat 7.1\n");
echo(" 550 on a dual 450 MHz UltraSPARC II running SunOS 5.8\n");
echo(" 1000 on a dual 500 MHz G4 PowerPC running Mac OS X 10.2\n");
echo(" 1500 on a dual 1.66 GHz Athlon MP 2000+ running RedHat 7.3\n");
echo(" 52000 on a 4x4 CPU 2.93 GHz Xeon running RHEL Server 5.4\n");
echo(" 65000 on a 512 CPU 400 MHz R12000 Running IRIX 6.5\n");
echo("\n");
}
}
}
{
/* TODO: !!! determine if this build is optimized or not */
/* TODO: !!! determine if this build has run-time debugging */
/* TODO: !!! determine if this build has compile-time debugging */
}
/* if this was a valid benchmark run, encourage submission of results. */
echo("You are encouraged to submit your benchmark results and system\n");
echo("configuration information to benchmark@brlcad.org\n");
echo(" ~~~~~~~~~~~~~~~~~~~~\n");
/* include information about the operating system and hardware in the log */
echo("Including additional kernel and hardware information in the log.\n\n");
/* TODO: !!! print out system information via sysctl/prtdiag/prtconf/hinv/etc */
bu_vls_free(&rtargs);
bu_vls_printf(&vp,
"%s/../share/brlcad/*.*.*/doc/benchmark.tr "
"%s/share/brlcad/*.*.*/doc/benchmark.tr "
"%s/share/brlcad/doc/benchmark.tr "
"%s/share/doc/benchmark.tr "
"%s/doc/benchmark.tr "
"%s/../doc/benchmark.tr "
"./benchmark.tr",
thisp, thisp, thisp, thisp, thisp, thisp);
bu_argv_from_string(argv, 32, bu_vls_addr(&vp));
look_for(NULL, file, "BENCHMARK_TR", "benchmark", (const char **)argv);
bu_vls_trunc(&vp, 0);
/* TODO: look for benchmark document here? */
echo("Output was saved to %s from %s\n", LOG, bu_dir(NULL, 0, BU_DIR_CURR, NULL));
echo("Benchmark testing complete.\n");
return 0;
}
/*
* Local Variables:
* tab-width: 8
* mode: C
* indent-tabs-mode: t
* c-file-style: "stroustrup"
* End:
* ex: shiftwidth=4 tabstop=8
*/
-96
View File
@@ -1,96 +0,0 @@
/* C L E A N . C
* BRL-CAD
*
* Copyright (c) 2011-2026 United States Government as represented by
* the U.S. Army Research Laboratory.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above
* copyright notice, this list of conditions and the following
* disclaimer in the documentation and/or other materials provided
* with the distribution.
*
* 3. The name of the author may not be used to endorse or promote
* products derived from this software without specific prior written
* permission.
*
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS
* OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
* DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE
* GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
* NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
/** @file clean.c
*
* utility functions to clean output files
*
*/
#include "common.h"
#include "bu/file.h"
#include "bu/str.h"
#include "bu/vls.h"
/* TODO: !!! needed */
//int bu_file_move(const char *fn1, const char *fn2) {if (!fn1 || !fn2) return -1; return 0;}
extern int bu_file_copy(const char *fn1, const char *fn2);
/**
* conditionally removes or saves any .pix or .log files output.
*/
void
clean_obstacles(const char *base_filename, int id)
{
struct bu_vls vp = BU_VLS_INIT_ZERO;
struct bu_vls vpid = BU_VLS_INIT_ZERO;
if (BU_STR_EMPTY(base_filename))
return;
/* look for an image file */
bu_vls_printf(&vp, "%s.pix", base_filename);
if (bu_file_exists(bu_vls_cstr(&vp), NULL)) {
bu_vls_printf(&vpid, "%s-%d.pix", base_filename, id);
if (bu_file_exists(bu_vls_cstr(&vpid), NULL)) {
bu_file_delete(bu_vls_cstr(&vp));
}
//bu_file_move(bu_vls_cstr(&vp), bu_vls_cstr(&vpid));
}
/* look for a log file */
bu_vls_printf(&vp, "%s.log", base_filename);
if (bu_file_exists(bu_vls_cstr(&vp), NULL)) {
bu_vls_printf(&vpid, "%s-%d.log", base_filename, id);
if (bu_file_exists(bu_vls_cstr(&vpid), NULL)) {
bu_file_delete(bu_vls_cstr(&vp));
}
//bu_file_move(bu_vls_cstr(&vp), bu_vls_cstr(&vpid));
}
}
/*
* Local Variables:
* tab-width: 8
* mode: C
* indent-tabs-mode: t
* c-file-style: "stroustrup"
* End:
* ex: shiftwidth=4 tabstop=8
*/
-96
View File
@@ -1,96 +0,0 @@
/* C O M P U T E . C
* BRL-CAD
*
* Copyright (c) 2011-2026 United States Government as represented by
* the U.S. Army Research Laboratory.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above
* copyright notice, this list of conditions and the following
* disclaimer in the documentation and/or other materials provided
* with the distribution.
*
* 3. The name of the author may not be used to endorse or promote
* products derived from this software without specific prior written
* permission.
*
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS
* OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
* DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE
* GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
* NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
/** @file compute.c
*
* run and computation functions
*
*/
#include "common.h"
/**
* average [..numbers..]
*
* computes the integer average for a set of given numbers
*/
double
average(int ac, double av[])
{
double total = 0.0;
if (ac < 1)
return -0.0;
while (ac-- > 0) {
total += av[ac];
}
return total / ac;
}
double
variance(int ac, double av[])
{
double avg;
double err = 0.0;
double num = ac;
if (ac < 1)
return -0.0;
else if (ac == 1)
return 0.0;
avg = average(ac, av);
/* compute variance numerator for the population */
while (ac-- > 0) {
err += (av[ac] - avg) * (av[ac] - avg);
}
/* return the sample variance */
return err / (num - 1);
}
/*
* Local Variables:
* tab-width: 8
* mode: C
* indent-tabs-mode: t
* c-file-style: "stroustrup"
* End:
* ex: shiftwidth=4 tabstop=8
*/
Executable
+158
View File
@@ -0,0 +1,158 @@
#!/bin/sh
# A Shell script to test LGT
# @(#)$Header$ (BRL)
# Ensure /bin/sh
export PATH || (echo "This isn't sh."; sh $0 $*; kill $$)
eval `machinetype.sh -b` # sets MACHINE, UNIXTYPE, HAS_TCP
if test -f ../.lgt.$MACHINE/lgt
then
LGT=../.lgt.$MACHINE/lgt
DB=../.db.$MACHINE
LD_LIBRARY_PATH=../.libcursor.$MACHINE:../.libtermio.$MACHINE:../.libbu.$MACHINE:../.libbn.$MACHINE:../.librt.$MACHINE:../.libfb.$MACHINE:../.libpkg.$MACHINE:../.libsysv.$MACHINE:$LD_LIBRARY_PATH
else
if test -f ../lgt/lgt
then
echo "Can't find LGT"
exit 1
fi
LGT=../lgt/lgt
DB=../db
LD_LIBRARY_PATH=../libcursor:../libtermio:../libbu:../libbn:../librt:../libfb:../libpkg:../libsysv:$LD_LIBRARY_PATH
fi
export LD_LIBRARY_PATH
CMP=./pixcmp
if test ! -f $CMP
then
cake pixcmp
fi
# Alliant NFS hack
if test x${MACHINE} = xfx
then
cp ${LGT} /tmp/lgt
cp ${CMP} /tmp/pixcmp
LGT=/tmp/lgt
CMP=/tmp/pixcmp
fi
# This test of LGT assumes a "live" framebuffer here.
if test x$FB_FILE = x
then
echo "Environment variable FB_FILE must be set to a real framebuffer"
echo "for this test of LGT to operate correctly."
exit 1
fi
# Run the first set of tests
${LGT} ${DB}/lgt-test.g all.g << EOF
# read light source data base
v ../db/lgt-test.ldb
# read material data base
w ../db/lgt-test.mdb
# force display window to be 512x512 pixels, should cause 8-to-1 zoom
T 512
# clear frame buffer
E
# set maximum bounces to 20
K 20
# turn hidden-line drawing off
k 0
# configure grid: 64 rays across
G 64 0 0 0.0
# turn perspective off
p 0
# change background to mauve
b 111 66 66
# read key frame
j ../db/lgt-test.key
# display view #3
R
# save image in file
H lgt3a.pix
# change frame buffer to disk file
o lgt3b.pix
# save a script of previous commands, to produce the "b" version.
S script3
# disable reading of key frame file
j
# change frame buffer back to default
o
# configure grid: 2.45 mm cells, centered about model origin, view size 225 mm
G 2.45 1 1 225.0
# change background to firebrick
b 142 35 35
# force frame buffer size to be 455 pixels across, should cause 4-to-1 zoom
T 455
# set automatic perspective at 0.25
p 0.25
# set anti-aliasing over-sampling factor to 2
A 2
# set maximum bounces to 20
K 20
# display view #1
R
# save image in file
H lgt1a.pix
# change frame buffer to disk file
o lgt1b.pix
# save a script
S script1
# change frame buffer back to default
o
# turn off anti-aliasing
A 1
# revert to auto-sizing of frame buffer
T 0
# set automatic perspective at 0.25
p 0.25
# select hidden-line drawing, reverse video
k 2
# configure grid: 128 rays across, centered at model RPP, view size 225mm
G 128 0 0 225.0
# display view #2
R
# save image in file
H lgt2a.pix
# change frame buffer to disk file
o lgt2b.pix
# save a script
S script2
# change frame buffer back to default
o
# bye
q
EOF
if test $? = 0
then :;
else echo "Abnormal lgt exit"; exit 1
fi
# Run the second set of tests. The scripts were created above.
./script1 < /dev/null &&
./script2 < /dev/null &&
./script3 < /dev/null || { echo "Script test failed."; exit 1; }
FAIL=0
for i in 1 2 3
do
if ${CMP} ../pix/lgt${i}.pix lgt${i}a.pix
then :;
else echo "Test $i A failed."; FAIL=1
fi
if ${CMP} ../pix/lgt${i}.pix lgt${i}b.pix
then :;
else echo "Test $i B failed."; FAIL=1
fi
done
if test "$FAIL" -eq 0
then
echo "LGT Tested OK."
exit 0
fi
echo "*** LGT does NOT work on this platform ***"
exit 2
Executable
+74
View File
@@ -0,0 +1,74 @@
#!/bin/sh
# A Shell script to extract the benchmark statistics, and build an
# entry suitable for the tables in doc/benchmark.doc.
# Note well that the command-line args may have embedded spaces.
# Mike Muuss & Susan Muuss, 11-Sept-88.
# @(#)$Header$ (BRL)
# Ensure /bin/sh
export PATH || (sh $0 $*; kill $$)
NAME=$0
if test "x$1" = x
then
echo "Usage: $NAME hostname [note1] [note2]"
exit 1
fi
# Save three args, because arg list will be reused below.
# They may have embedded spaces in them.
HOST="$1"
NOTE1="$2"
NOTE2="$3"
NEW_FILES="moss.log world.log star.log bldg391.log m35.log sphflake.log"
REF_FILES="../pix/moss.log ../pix/world.log ../pix/star.log \
../pix/bldg391.log ../pix/m35.log ../pix/sphflake.log"
for i in $NEW_FILES $REF_FILES
do
if test ! -f $i
then
echo "${NAME}: file $i does not exist, aborting"
exit 1
fi
done
# Use TR to convert newlines to tabs.
VGRREF=`grep RTFM $REF_FILES | \
sed -n -e 's/^.*= *//' -e 's/ rays.*//p' | \
tr '\012' '\011' `
CURVALS=`grep RTFM $NEW_FILES | \
sed -n -e 's/^.*= *//' -e 's/ rays.*//p' | \
tr '\012' '\011' `
RATIO_LIST=""
# Trick: Force args $1 through $6 to the numbers in $CURVALS
# This should be "set -- $CURVALS", but 4.2BSD /bin/sh can't handle it,
# and CURVALS are all positive (ie, no leading dashes), so this is safe.
set $CURVALS
while test $# -lt 6
do echo "${NAME}: Warning, only $# times found, adding a zero."
CURVALS="${CURVALS}0 "
set $CURVALS
done
for ref in $VGRREF
do
cur=$1
shift
RATIO=`echo "2k $cur $ref / p" | dc`
# Note: append new value and a trail TAB to existing list.
RATIO_LIST="${RATIO_LIST}$RATIO "
done
# The number of plus signs must be one less than the number of elements.
MEAN_ABS=`echo 2k $CURVALS +++++ 6/ p | dc`
MEAN_REL=`echo 2k $RATIO_LIST +++++ 6/ p | dc`
# Note: Both RATIO_LIST and CURVALS have an extra trailing tab.
# The question mark is for the mean field
echo "Abs ${HOST} ${CURVALS}${MEAN_ABS} $NOTE1"
echo "*vgr ${HOST} ${RATIO_LIST}${MEAN_REL} $NOTE2"
+108 -488
View File
@@ -1,514 +1,134 @@
/* P I X C M P . C
* BRL-CAD
/*
* P I X C M P . C
*
* Copyright (c) 2004-2026 United States Government as represented by
* the U.S. Army Research Laboratory.
* Compute the difference between two .pix files.
* To establish context, a monochrome image is produced when there
* are no differences; otherwise the channels that differ are
* highlighted on differing pixels.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public License
* version 2.1 as published by the Free Software Foundation.
* This routine operates on a pixel-by-pixel basis, and thus
* is independent of the resolution of the image.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this file; see the file named COPYING for more
* information.
*
*/
/** @file pixcmp.c
*
* Compute and summarily report differences between two .pix files.
*
* This routine operates on a pixel-by-pixel basis, and thus
* is independent of the resolution of the image.
* Author -
* Charles M. Kennedy
* Michael John Muuss
*
* Source -
* SECAD/VLD Computing Consortium, Bldg 394
* The U. S. Army Ballistic Research Laboratory
* Aberdeen Proving Ground, Maryland 21005
*
* Copyright Notice -
* This software is Copyright (C) 1988-2004 by the United States Army.
* All rights reserved.
*/
#ifndef lint
static const char RCSid[] = "@(#)$Header$ (BRL)";
#endif
#include "common.h"
#include "conf.h"
#include <stdio.h>
#include <stdlib.h>
#ifdef HAVE_STRING_H
#include <string.h>
#ifdef HAVE_SYS_STAT_H
# include <sys/stat.h>
#endif
#include "bio.h"
// TODO - replace with std::filesystem::is_fifo
#ifndef S_ISFIFO
# ifdef S_IFIFO
# define S_ISFIFO(mode) (((mode) & S_IFMT) == S_IFIFO)
# else
# define S_ISFIFO(mode) (0)
# endif
#endif
#include <errno.h>
#include "bu/app.h"
#include "bu/getopt.h"
#include "bu/log.h"
#include "bu/file.h"
#include "bu/str.h"
long matching;
long off1;
long offmany;
/* exit codes for argument processing errors */
#define OPTS_ERROR 127
#define FILE_ERROR 126
char usage[] = "Usage: pixcmp f1.pix f2.pix\n";
/* exit codes for normal operation */
#define EXIT_OFF_BY_NONE 0
#define EXIT_OFF_BY_ONE 1
#define EXIT_OFF_BY_MANY 2
enum diff {
MATCHING,
OFF_BY_ONE,
OFF_BY_MANY,
MISSING
};
static void
usage(const char *name)
{
const char *unknown = "pixcmp";
if (!name) {
name = unknown;
}
/* split to fit within ISO C90 max static string length < 509 chars */
bu_log("Usage: %s [OPTIONS] FILE1 [FILE2 [SKIP1 [SKIP2]]]\n"
"\n"
" Compare two PIX files pixel by pixel (or byte by byte), optionally"
" skipping initial pixels (or bytes) in one or both input files.\n"
"\n", name);
bu_log("Options:"
" -b Iterate and print by bytes instead of by pixels.\n"
" -s Print all that have the same matching values.\n"
" -d Print all that have different values.\n"
" -q Quiet. Suppress printing header and summary.\n"
" -i SKIP\n"
" Discard initial SKIP pixels (or bytes w/ -b) in FILE1 and FILE2 input.\n"
" -i SKIP1:SKIP2\n"
" Skip initial SKIP1 pixels (or bytes w/ -b) in FILE1 and SKIP2 in FILE2.\n"
" -n COUNT\n"
" Compare COUNT pixels (or bytes w/ -b). Stops by default at EOF.\n"
"\n");
bu_log("If either FILE is `-' or is missing, then input is read from standard input.\n"
"If FILE1 and FILE2 are both standard input, then values must be interleaved.\n"
"If the `-b' option is used, SKIP and COUNT values are bytes instead of pixels.\n"
"Pixel numbers and bytes are indexed linearly from one.\n"
"\n");
return;
}
static void
handle_range_opt(const char *arg, size_t *skip1, size_t *skip2)
{
const char *endptr = arg;
long val;
if ((arg == NULL) || ((skip1 == NULL) && (skip2 == NULL))) {
/* nothing to do */
return;
}
while ((endptr != NULL) && (endptr[0] != ':') && (endptr[0] != '\0')) {
endptr++;
}
if (endptr == arg) {
/* probably empty string */
if (skip2) {
endptr++;
val = strtol(endptr, NULL, 10);
*skip2 = (val < 0) ? 0 : val;
}
} else if ((endptr == NULL) || (endptr[0] == '\0')) {
/* no : found */
if (skip2) {
val = strtol(arg, NULL, 10);
*skip2 = (val < 0) ? 0 : val;
}
if (skip1 && skip2) {
*skip1 = *skip2;
}
} else if (endptr[0] == ':') {
/* found : */
if (skip1) {
val = strtol(arg, NULL, 10);
*skip1 = (val < 0) ? 0 : val;
}
if (skip2) {
endptr++; /* skip over : */
val = strtol(endptr, NULL, 10);
*skip2 = (val < 0) ? 0 : val;
}
} else {
bu_exit(OPTS_ERROR, "Unexpected input processing [%s]\n", arg);
}
}
static enum diff
compare_rgb(int r1, int g1, int b1, int r2, int g2, int b2, size_t *matching, size_t *off1, size_t *offmany, size_t *missing)
{
enum diff result = MISSING;
if ((r1 == r2 && r1 != -1)
&& (g1 == g2 && g1 != -1)
&& (b1 == b2 && b1 != -1))
{
result = MATCHING;
} else if (r1 == -1 || r2 == -1 || g1 == -1 || g2 == -1 || b1 == -1 || b2 == -1) {
/* image sizes don't match (or other I/O error) */
result = MISSING;
} else {
/* at least this */
result = OFF_BY_ONE;
/* but maybe more */
if (r1 != r2) {
if ((r1 > r2 ? r1 - r2 : r2 - r1) > 1) {
result = OFF_BY_MANY;
}
}
if (g1 != g2) {
if ((g1 > g2 ? g1 - g2 : g2 - g1) > 1) {
result = OFF_BY_MANY;
}
}
if (b1 != b2) {
if ((b1 > b2 ? b1 - b2 : b2 - b1) > 1) {
result = OFF_BY_MANY;
}
}
}
if (result == OFF_BY_ONE) {
(*off1)++;
} else if (result == OFF_BY_MANY) {
(*offmany)++;
} else if (result == MATCHING) {
(*matching)++;
} else {
(*missing)++;
}
return result;
}
int main(int argc, char **argv);
int
main(int argc, char *argv[])
main(int argc, char **argv)
{
const char *argv0 = argv[0];
register FILE *f1, *f2;
FILE *f1 = NULL;
FILE *f2 = NULL;
struct stat sf1;
struct stat sf2;
memset(&sf1, 0, sizeof(struct stat));
memset(&sf2, 0, sizeof(struct stat));
size_t matching = 0;
size_t off1 = 0;
size_t offmany = 0;
size_t missing = 0;
int c;
int list_diff = 0;
int list_same = 0;
int print_bytes = 0;
int quiet = 0;
size_t bytes = 0;
size_t f1_skip = 0;
size_t f2_skip = 0;
size_t stop_after = 0;
bu_setprogname(argv[0]);
/* process opts */
while ((c = bu_getopt(argc, argv, "sdbi:n:q?")) != -1) {
switch (c) {
case 's':
list_same = 1;
break;
case 'd':
list_diff = 1;
break;
case 'b':
print_bytes = 1;
break;
case 'i':
handle_range_opt(bu_optarg, &f1_skip, &f2_skip);
break;
case 'n':
{
long num = strtol(bu_optarg, NULL, 10);
stop_after = (num < 0) ? 0 : num;
break;
}
case 'q':
quiet = 1;
break;
case '?':
case 'h':
usage(argv0);
return 0;
default:
exit(OPTS_ERROR);
}
}
argc -= bu_optind;
argv += bu_optind;
/* validate what is left over */
if (argc < 1 || argc > 4) {
bu_log("ERROR: incorrect number of arguments provided\n\n");
usage(argv0);
exit(OPTS_ERROR);
}
if ((argc > 0 && !argv[0]) || (argc > 1 && !argv[1])) {
bu_log("ERROR: bad filename\n\n");
usage(argv0);
exit(OPTS_ERROR);
}
if ((argc > 2 && !argv[2]) || (argc > 3 && !argv[3])) {
bu_log("ERROR: bad skip value\n\n");
usage(argv0);
exit(OPTS_ERROR);
}
/* handle optional SKIP1 and SKIP2 following filenames */
if (argc > 2) {
char range[64] = {0};
if (argc > 3) {
snprintf(range, 64, "%s:%s", argv[2], argv[3]);
} else {
snprintf(range, 64, "%s", argv[2]);
}
handle_range_opt(range, &f1_skip, &f2_skip);
}
if (!print_bytes) {
if ((f1_skip > ((size_t)-1)/3)
|| (f2_skip > ((size_t)-1)/3))
{
bu_log("ERROR: overflow, -i skip value(s) are too big {%zu:%zu}\n", f1_skip, f2_skip);
exit(OPTS_ERROR);
}
f1_skip *= 3;
f2_skip *= 3;
if (stop_after > ((size_t)-1)/3)
{
bu_log("ERROR: overflow, -n number is too big {%zu}\n", stop_after);
exit(OPTS_ERROR);
}
stop_after *= 3;
}
if (BU_STR_EQUAL(argv[0], "-")) {
f1 = stdin;
} else if ((f1 = fopen(argv[0], "rb")) == NULL) {
perror(argv[0]);
exit(FILE_ERROR);
}
if ((argc < 2) || BU_STR_EQUAL(argv[1], "-")) {
f2 = stdin;
} else if ((f2 = fopen(argv[1], "rb")) == NULL) {
perror(argv[1]);
exit(FILE_ERROR);
}
setmode(fileno(stdin), O_BINARY);
/* we're writing out ascii */
/* setmode(fileno(stdout), O_BINARY); */
if (f1_skip != f2_skip && f1 == stdin && f2 == stdin) {
bu_exit(OPTS_ERROR, "ERROR: cannot skip the same input stream by different amounts\n");
}
errno = 0;
if (fstat(fileno(f1), &sf1)) {
bu_log("Warning - f1 fstat failed: %s\n", strerror(errno));
}
errno = 0;
if (fstat(fileno(f2), &sf2)) {
bu_log("Warning - f2 fstat failed: %s\n", strerror(errno));
}
/* bu_log("FILE1_size(%zu) FILE1_skip(%zu) FILE2_size(%zu) FILE2_skip(%zu)\n", (size_t)sf1.st_size, f1_skip, (size_t)sf2.st_size, f2_skip); */
if (!quiet && ((sf1.st_size - f1_skip) != (sf2.st_size - f2_skip))) {
bu_log("WARNING: Different image sizes detected\n");
if (print_bytes) {
bu_log("\t%s: %7zu bytes (%8zu bytes, skipping %7zu)\n",
argv[0], (size_t)sf1.st_size - f1_skip, (size_t)sf1.st_size, f1_skip);
bu_log("\t%s: %7zu bytes (%8zu bytes, skipping %7zu)\n",
argv[1], (size_t)sf2.st_size - f2_skip, (size_t)sf2.st_size, f2_skip);
} else {
bu_log("\t%s: %7zu pixels (%8zu bytes, skipping %7zu)\n",
argv[0], ((size_t)sf1.st_size - f1_skip)/3, (size_t)sf1.st_size, f1_skip);
bu_log("\t%s: %7zu pixels (%8zu bytes, skipping %7zu)\n",
argv[1], ((size_t)sf2.st_size - f2_skip)/3, (size_t)sf2.st_size, f2_skip);
}
}
/* make sure we read all bytes */
if (stop_after == 0) {
stop_after = FMAX((sf1.st_size - f1_skip), (sf2.st_size - f2_skip));
if (f1 == stdin && f2 == stdin) {
/* dual stdin is interleaved */
stop_after = (stop_after+1)/2;
}
}
/*
bu_log("mode is [%d] and [%d]\n", S_ISFIFO(sf1.st_mode), S_ISFIFO(sf2.st_mode));
bu_log("tty is [%d] and [%d]\n", isatty(fileno(f1)), isatty(fileno(f2)));
*/
/* skip requested pixels/bytes in FILE1 */
if (f1_skip) {
if (S_ISFIFO(sf1.st_mode)) {
size_t skipped = 0;
for (skipped = 0; skipped < f1_skip; skipped++) {
(void)fgetc(f1);
}
} else if (fseek(f1, (long)f1_skip, SEEK_SET)) {
bu_log("ERROR: Unable to seek %zd %s%s in FILE1\n",
f1_skip,
print_bytes?"byte":"pixel",
f1_skip==1?"":"s");
perror("FILE1 fseek failure");
exit(FILE_ERROR);
}
}
/* skip requested pixels in FILE2 */
if (f2_skip) {
if (S_ISFIFO(sf2.st_mode)) {
size_t skipped = 0;
for (skipped = 0; skipped < f2_skip; skipped++) {
(void)fgetc(f2);
}
} else if (fseek(f2, (long)f2_skip, SEEK_SET)) {
bu_log("ERROR: Unable to seek %zd %s%s in FILE2\n",
f2_skip,
print_bytes?"byte":"pixel",
f2_skip==1?"":"s");
perror("FILE2 fseek failure");
exit(FILE_ERROR);
}
}
/* print header to stderr, output to stdout */
if (!quiet && (list_same || list_diff)) {
if (print_bytes) {
bu_log("#Byte FILE1 FILE2 LABEL\n");
} else {
bu_log("#Pixel\t(FILE1 R, G, B) (FILE2 R, G, B)\n");
}
}
/* iterate over the pixels/bytes in the files */
while (bytes < stop_after) {
enum diff result;
int r1 = -1;
int r2 = -1;
int g1 = -1;
int g2 = -1;
int b1 = -1;
int b2 = -1;
/* bu_log("\tbytes[%zu] < stop[%zu\n", bytes, stop_after); */
r1 = fgetc(f1);
r2 = fgetc(f2);
bytes++;
if (print_bytes) {
/* replicate */
b1 = g1 = 0;
b2 = g2 = 0;
} else {
g1 = fgetc(f1);
g2 = fgetc(f2);
bytes++;
b1 = fgetc(f1);
b2 = fgetc(f2);
bytes++;
if( argc != 3 ) {
fprintf(stderr, "%s", usage);
exit(0);
}
result = compare_rgb(r1, g1, b1, r2, g2, b2, &matching, &off1, &offmany, &missing);
/* print them? */
if ((result==MATCHING && list_same)
|| (result!=MATCHING && list_diff))
{
const char *label = NULL;
switch (result) {
case MATCHING:
label = "MATCHING";
break;
case OFF_BY_MANY:
label = "OFF_BY_MANY";
break;
case OFF_BY_ONE:
label = "OFF_BY_ONE";
break;
case MISSING:
default:
label = "MISSING";
break;
}
if (print_bytes) {
printf("%zu %3d %3d %s\n", bytes, r1, r2, label);
} else {
printf("%zu\t(%3d, %3d, %3d)\t(%3d, %3d, %3d) %s\n", bytes / 3, r1, g1, b1, r2, g2, b2, label);
}
if( strcmp( argv[1], "-" ) == 0 )
f1 = stdin;
else if( (f1 = fopen( argv[1], "r" ) ) == NULL ) {
perror( argv[1] );
exit(1);
}
}
/* print summary */
if (!quiet) {
printf("pixcmp %s: %8zd matching, %8zd off by 1, %8zd off by many",
print_bytes?"bytes":"pixels", matching, off1, offmany);
if (missing) {
printf(", %8zd missing\n", missing);
} else {
printf("\n");
if( strcmp( argv[2], "-" ) == 0 )
f2 = stdin;
else if( (f2 = fopen( argv[2], "r" ) ) == NULL ) {
perror( argv[2] );
exit(1);
}
}
while(1) {
register int r1, g1, b1;
int r2, g2, b2;
/* check for errors */
if (ferror(f1) || ferror(f2)) {
perror("pixcmp file error");
return FILE_ERROR;
}
r1 = fgetc( f1 );
g1 = fgetc( f1 );
b1 = fgetc( f1 );
r2 = fgetc( f2 );
g2 = fgetc( f2 );
b2 = fgetc( f2 );
if( feof(f1) || feof(f2) ) break;
/* indicate how many differences there were overall */
if (offmany || missing) {
return EXIT_OFF_BY_MANY;
}
if (off1) {
return EXIT_OFF_BY_ONE;
}
if( r1 != r2 || g1 != g2 || b1 != b2 ) {
register int i;
/* Success! */
return EXIT_OFF_BY_NONE;
/* Highlight differing channels */
if( r1 != r2 ) {
if( (i = r1 - r2) < 0 ) i = -i;
if( i > 1 ) {
offmany++;
} else {
off1++;
}
} else {
matching++;
}
if( g1 != g2 ) {
if( (i = g1 - g2) < 0 ) i = -i;
if( i > 1 ) {
offmany++;
} else {
off1++;
}
} else {
matching++;
}
if( b1 != b2 ) {
if( (i = b1 - b2) < 0 ) i = -i;
if( i > 1 ) {
offmany++;
} else {
off1++;
}
} else {
matching++;
}
} else {
/* Common case: equal. Give B&W NTSC average */
matching += 3;
}
}
fprintf(stderr,
"pixcmp bytes: %8ld matching, %8ld off by 1, %8ld off by many\n",
matching, off1, offmany );
/* If files were of different lengths, that is an error */
if( feof(f1) != feof(f2) )
exit(2);
/* If any pixels were off by more than +/- 1, that is an error */
if( offmany)
exit(1);
/* Success! */
exit(0);
}
/*
* Local Variables:
* mode: C
* tab-width: 8
* indent-tabs-mode: t
* c-file-style: "stroustrup"
* End:
* ex: shiftwidth=4 tabstop=8
*/
-80
View File
@@ -1,80 +0,0 @@
# Exercise pixcmp's pixel tolerance and exit-status contract with small,
# deliberately readable byte streams.
if(NOT PIXCMP OR NOT TEST_DIR)
message(FATAL_ERROR "PIXCMP and TEST_DIR are required")
endif()
function(check_pixcmp name input1 input2 expected_status expected_summary)
set(file1 "${TEST_DIR}/pixcmp_${name}_1.pix")
set(file2 "${TEST_DIR}/pixcmp_${name}_2.pix")
file(WRITE "${file1}" "${input1}")
file(WRITE "${file2}" "${input2}")
execute_process(
COMMAND "${PIXCMP}" ${ARGN} "${file1}" "${file2}"
OUTPUT_VARIABLE output
ERROR_VARIABLE errors
RESULT_VARIABLE status
)
file(REMOVE "${file1}" "${file2}")
if(NOT "${status}" STREQUAL "${expected_status}")
message(
FATAL_ERROR
"${name}: pixcmp returned ${status}, expected ${expected_status}\nstdout: ${output}\nstderr: ${errors}"
)
endif()
string(REGEX REPLACE "[ \t\r\n]+" " " normalized_output "${output}")
string(STRIP "${normalized_output}" normalized_output)
string(FIND "${normalized_output}" "${expected_summary}" summary_position)
if(summary_position EQUAL -1)
message(
FATAL_ERROR
"${name}: expected summary '${expected_summary}'\nactual stdout: ${output}\nstderr: ${errors}"
)
endif()
endfunction()
set(exact_pixel "pixcmp pixels: 1 matching, 0 off by 1, 0 off by many")
set(tolerated_pixel "pixcmp pixels: 0 matching, 1 off by 1, 0 off by many")
set(rejected_pixel "pixcmp pixels: 0 matching, 0 off by 1, 1 off by many")
check_pixcmp(exact "ABC" "ABC" 0 "${exact_pixel}")
check_pixcmp(one_channel_within_tolerance "ABC" "BBC" 1 "${tolerated_pixel}")
check_pixcmp(two_channels_within_tolerance "ABC" "BCC" 1 "${tolerated_pixel}")
check_pixcmp(three_channels_within_tolerance "ABC" "@CB" 1 "${tolerated_pixel}")
# Keep the tolerated channel first in two cases to catch short-circuiting that
# would fail to inspect a later channel outside the tolerance.
check_pixcmp(red_outside_tolerance "ABC" "CCD" 2 "${rejected_pixel}")
check_pixcmp(green_outside_tolerance "ABC" "BDD" 2 "${rejected_pixel}")
check_pixcmp(blue_outside_tolerance "ABC" "BCE" 2 "${rejected_pixel}")
check_pixcmp(
missing_pixel
"ABC"
"ABCDEF"
2
"pixcmp pixels: 1 matching, 0 off by 1, 0 off by many, 1 missing"
)
check_pixcmp(
byte_within_tolerance
"A"
"B"
1
"pixcmp bytes: 0 matching, 1 off by 1, 0 off by many"
-b
)
check_pixcmp(
byte_outside_tolerance
"A"
"C"
2
"pixcmp bytes: 0 matching, 0 off by 1, 1 off by many"
-b
)
+43
View File
@@ -0,0 +1,43 @@
#!/bin/sh
export PATH || (echo "This isn't sh."; sh $0 $*; kill $$)
eval `machinetype.sh -b` # sets MACHINE, UNIXTYPE, HAS_TCP
if test -f ../.rt.$MACHINE/rt
then
RT=../.rt.$MACHINE/rt
DB=../.db.$MACHINE
LD_LIBRARY_PATH=../.libbu.$MACHINE:../.libbn.$MACHINE:../.librt.$MACHINE:../.libfb.$MACHINE:../.libpkg.$MACHINE:../.libsysv.$MACHINE:$LD_LIBRARY_PATH
else
if test ! -f ../rt/rt
then
echo "Can't find RT"
exit 1
fi
RT=../rt/rt
DB=../db
LD_LIBRARY_PATH=../libbu:../libbn:../librt:../libfb:../libpkg:../libsysv:$LD_LIBRARY_PATH
fi
export LD_LIBRARY_PATH
# Alliant NFS hack
if test x${MACHINE} = xfx
then
cp ${RT} /tmp/rt
RT=/tmp/rt
fi
# WARNING THIS IS A REAL CPU HOG
if test -f cube.pix; then mv -f cube.pix cube.pix.$$; fi
if test -f cube.log; then mv -f cube.log cube.log.$$; fi
$RT -p90 -f1024 -H3 -M $*\
-o cube.pix\
$DB/cube.g\
'all.g' \
2> cube.log\
<<EOF
6.847580140e+03
3.699276190e+03 3.032924070e+03 3.658674860e+03
-5.735762590e-01 8.191521640e-01 0.000000000e+00 0.000000000e+00
-3.461885920e-01 -2.424037690e-01 9.063078880e-01 0.000000000e+00
7.424040310e-01 5.198366640e-01 4.226181980e-01 0.000000000e+00
0.000000000e+00 0.000000000e+00 0.000000000e+00 1.000000000e+00
EOF
+52
View File
@@ -0,0 +1,52 @@
#!/bin/sh
# A Shell script to re-check the most recent results of the benchmark
# @(#)$Header$ (BRL)
# Ensure /bin/sh
export PATH || (echo "This isn't sh."; sh $0 $*; kill $$)
eval `machinetype.sh -b` # sets MACHINE, UNIXTYPE, HAS_TCP
if test -f ../.util.$MACHINE/pixdiff
then
PIXDIFF=../.util.$MACHINE/pixdiff
PIX_FB=../.fb.$MACHINE/pix-fb
LD_LIBRARY_PATH=../.libbu.$MACHINE:../.libbn.$MACHINE:../.librt.$MACHINE:../.libfb.$MACHINE:../.libpkg.$MACHINE:../.libsysv.$MACHINE:$LD_LIBRARY_PATH
else
if test -f ../util/pixdiff
then
PIXDIFF=../util/pixdiff
PIX_FB=../fb/pix-fb
else
echo "Can't find pixdiff"
exit 1
fi
LD_LIBRARY_PATH=../libbu:../libbn:../librt:../libfb:../libpkg:../libsysv:$LD_LIBRARY_PATH
fi
export LD_LIBRARY_PATH
# Alliant NFS hack
if test x${MACHINE} = xfx
then
cp ${PIXDIFF} /tmp/pixdiff
cp ${PIX_FB} /tmp/pix-fb
PIXDIFF=/tmp/pixdiff
PIX_FB=/tmp/pix-fb
fi
echo +++++ moss.pix
${PIXDIFF} ../pix/moss.pix moss.pix | ${PIX_FB}
echo +++++ world.pix
${PIXDIFF} ../pix/world.pix world.pix | ${PIX_FB}
echo +++++ star.pix
${PIXDIFF} ../pix/star.pix star.pix | ${PIX_FB}
echo +++++ bldg391.pix
${PIXDIFF} ../pix/bldg391.pix bldg391.pix | ${PIX_FB}
echo +++++ m35.pix
${PIXDIFF} ../pix/m35.pix m35.pix | ${PIX_FB}
echo +++++ sphflake.pix
${PIXDIFF} ../pix/sphflake.pix sphflake.pix | ${PIX_FB}
-33
View File
@@ -1,33 +0,0 @@
set(
BENCHMARK_PIX
bldg391.pix
m35.pix
moss.pix
sphflake.pix
star.pix
world.pix
)
set(
PIX_LOG
bldg391.log
m35.log
moss.log
sphflake.log
star.log
world.log
)
brlcad_adddata(BENCHMARK_PIX pix)
brlcad_adddata(PIX_LOG pix)
cmakefiles(${BENCHMARK_PIX})
cmakefiles(${PIX_LOG})
cmakefiles(CMakeLists.txt)
# Local Variables:
# tab-width: 8
# mode: cmake
# indent-tabs-mode: t
# End:
# ex: shiftwidth=2 tabstop=8
-114
View File
@@ -1,114 +0,0 @@
/* R U N . C
* BRL-CAD
*
* Copyright (c) 2011-2026 United States Government as represented by
* the U.S. Army Research Laboratory.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above
* copyright notice, this list of conditions and the following
* disclaimer in the documentation and/or other materials provided
* with the distribution.
*
* 3. The name of the author may not be used to endorse or promote
* products derived from this software without specific prior written
* permission.
*
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS
* OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
* DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE
* GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
* NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
/** @file run.c
*
* run functions
*
*/
#include "common.h"
#include <stdlib.h>
#include "bu.h"
/* TODO: !!! obviously */
struct bu_vls bu_argv_to_string(int ac, const char *av[]) {struct bu_vls v = BU_VLS_INIT_ZERO; if (ac) {bu_vls_printf(&v, "%s", av[0]);} return v;}
int (*echo)(const char *, ...) = &bu_log;
extern int bu_exec(const char *program, void *data, struct bu_vls *out, struct bu_vls *err);
/**
* run file_prefix geometry hypersample [..rt args..]
* runs a single benchmark test assuming the following are preset:
*
* RT := path/name of the raytracer to use
* DB := path to the geometry file
*
* it is assumed that stdin will be the view/frame input
*/
int
run(int ac, char *av[])
{
int retval;
const char *run_geomname = av[0];
const char *run_geometry = av[1];
long int hypersample = strtod(av[2], NULL);
av += 3;
ac -= 3;
{
struct bu_vls args = bu_argv_to_string(ac, (const char **)av);
echo("DEBUG: Running %s -B -M -s512 -H%ld -J0 %s -o %s.pix %s/%s.g %s\n", av[0], hypersample, args, run_geomname, run_geomname, run_geometry);
bu_vls_free(&args);
}
/* pipe(stdin_for_bu_exec); */
retval = bu_exec("program", NULL, NULL, NULL);
echo("DEBUG: Running %s returned %d\n", av[0], retval);
return retval;
}
/**
* runs a series of benchmark tests assuming the following are preset:
*
* TIMEFRAME := maximum amount of wallclock time to spend per test
*
* is is assumed that stdin will be the view/frame input
*/
int
bench(const char *test_name)
{
if (!test_name)
return -1;
/* FIXME: !!! lots missing here */
return 0;
}
/*
* Local Variables:
* tab-width: 8
* mode: C
* indent-tabs-mode: t
* c-file-style: "stroustrup"
* End:
* ex: shiftwidth=4 tabstop=8
*/
+261 -1594
View File
File diff suppressed because it is too large Load Diff
+123 -64
View File
@@ -1,74 +1,133 @@
#!/bin/sh
# T R Y . S H
# BRL-CAD
#
# Copyright (c) 2004-2026 United States Government as represented by
# the U.S. Army Research Laboratory.
#
# Redistribution and use in source and binary forms, with or without
# modification, are permitted provided that the following conditions
# are met:
#
# 1. Redistributions of source code must retain the above copyright
# notice, this list of conditions and the following disclaimer.
#
# 2. Redistributions in binary form must reproduce the above
# copyright notice, this list of conditions and the following
# disclaimer in the documentation and/or other materials provided
# with the distribution.
#
# 3. The name of the author may not be used to endorse or promote
# products derived from this software without specific prior written
# permission.
#
# THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS
# OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
# WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
# DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE
# GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
# INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
# WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
# NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
# SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
#
###
# A Shell script to run the BRL-CAD Benchmark, with output going to
# a framebuffer rather than to a file.
#
# Authors -
# Mike Muuss
# Christopher Sean Morrison
#
# A Shell script to run the BRL-CAD Benchmark Test,
# with output going to the current framebuffer, rather than a file.
# @(#)$Header$ (BRL)
# Ensure /bin/sh
export PATH || (echo "This isn't sh."; sh $0 $*; kill $$)
path_to_this=`dirname $0`
# force locale setting to C so things like date output as expected
LC_ALL=C
eval `machinetype.sh -b` # sets MACHINE, UNIXTYPE, HAS_TCP
if test -f ../.rt.$MACHINE/rt
then
RT=../.rt.$MACHINE/rt
DB=../.db.$MACHINE
LD_LIBRARY_PATH=../.libbu.$MACHINE:../.libbn.$MACHINE:../.librt.$MACHINE:../.libfb.$MACHINE:../.libpkg.$MACHINE:../.libsysv.$MACHINE:$LD_LIBRARY_PATH
else
if test ! -f ../rt/rt
then
echo "Can't find RT"
exit 1
fi
RT=../rt/rt
DB=../db
LD_LIBRARY_PATH=../libbu:../libbn:../librt:../libfb:../libpkg:../libsysv:$LD_LIBRARY_PATH
fi
export LD_LIBRARY_PATH
TIMEFRAME=1 ; export TIMEFRAME
MAXTIME=1 ; export MAXTIME
ARGS="-F/dev/Xl $*"
if test -f "$path_to_this/run.sh" ; then
$path_to_this/run.sh $ARGS
elif test -f "$path_to_this/benchmark" ; then
$path_to_this/benchmark $ARGS
elif test -f "/usr/brlcad/bin/benchmark" ; then
/usr/brlcad/bin/benchmark $ARGS
CMP=./pixcmp
if test ! -f $CMP
then
cake pixcmp
fi
# Alliant NFS hack
if test x${MACHINE} = xfx
then
cp ${RT} /tmp/rt
cp ${CMP} /tmp/pixcmp
RT=/tmp/rt
CMP=/tmp/pixcmp
fi
# Run the tests
echo +++++ moss
time $RT -B -M -s512 $* \
$DB/moss.g all.g \
<< EOF
viewsize 1.572026215e+02;
eye_pt 6.379990387e+01 3.271768951e+01 3.366661453e+01;
viewrot -5.735764503e-01 8.191520572e-01 0.000000000e+00
0.000000000e+00 -3.461886346e-01 -2.424038798e-01 9.063078165e-01
0.000000000e+00 7.424039245e-01 5.198368430e-01 4.226182699e-01
0.000000000e+00 0.000000000e+00 0.000000000e+00 0.000000000e+00
1.000000000e+00 ;
start 0;
end;
EOF
echo +++++ world
time $RT -B -M -s512 $* \
$DB/world.g all.g \
<< EOF
viewsize 1.572026215e+02;
eye_pt 6.379990387e+01 3.271768951e+01 3.366661453e+01;
viewrot -5.735764503e-01 8.191520572e-01 0.000000000e+00
0.000000000e+00 -3.461886346e-01 -2.424038798e-01 9.063078165e-01
0.000000000e+00 7.424039245e-01 5.198368430e-01 4.226182699e-01
0.000000000e+00 0.000000000e+00 0.000000000e+00 0.000000000e+00
1.000000000e+00 ;
start 0;
end;
EOF
echo +++++ star
time $RT -B -M -s512 $* \
$DB/star.g all \
<<EOF
viewsize 2.500000000e+05;
eye_pt 2.102677960e+05 8.455500000e+04 2.934714650e+04;
viewrot -6.733560560e-01 6.130643360e-01 4.132114880e-01 0.000000000e+00
5.539599410e-01 4.823888300e-02 8.311441420e-01 0.000000000e+00
4.896120540e-01 7.885590550e-01 -3.720948210e-01 0.000000000e+00
0.000000000e+00 0.000000000e+00 0.000000000e+00 1.000000000e+00 ;
start 0;
end;
EOF
echo +++++ bldg391
time $RT -B -M -s512 $* \
$DB/bldg391.g all.g \
<<EOF
viewsize 1.800000000e+03;
eye_pt 6.345012207e+02 8.633251343e+02 8.310771484e+02;
viewrot -5.735764503e-01 8.191520572e-01 0.000000000e+00
0.000000000e+00 -3.461886346e-01 -2.424038798e-01 9.063078165e-01
0.000000000e+00 7.424039245e-01 5.198368430e-01 4.226182699e-01
0.000000000e+00 0.000000000e+00 0.000000000e+00 0.000000000e+00
1.000000000e+00 ;
start 0;
end;
EOF
echo +++++ m35
time $RT -B -M -s512 $* \
$DB/m35.g all.g \
<< EOF
viewsize 6.787387985e+03;
eye_pt 3.974533127e+03 1.503320754e+03 2.874633221e+03;
viewrot -5.527838919e-01 8.332423558e-01 1.171090926e-02 0.000000000e+00
-4.815587087e-01 -3.308784486e-01 8.115544728e-01 0.000000000e+00
6.800964482e-01 4.429747496e-01 5.841593895e-01 0.000000000e+00
0.000000000e+00 0.000000000e+00 0.000000000e+00 1.000000000e+00 ;
start 0;
end;
EOF
echo +++++ sphflake
time $RT -B -M -s512 $* \
$DB/sphflake.g scene.r \
<< EOF
viewsize 2.556283261452611e+04;
orientation 4.406810841785839e-01 4.005093234738861e-01 5.226451688385938e-01 6.101102288499644e-01;
eye_pt 2.418500583758302e+04 -3.328563644344796e+03 8.489926952850350e+03;
start 0;
end;
EOF
# Local Variables:
# mode: sh
# tab-width: 8
# sh-indentation: 4
# sh-basic-offset: 4
# indent-tabs-mode: t
# End:
# ex: shiftwidth=4 tabstop=8
-183
View File
@@ -1,183 +0,0 @@
#!/bin/sh
# V I E W D I F F . S H
# BRL-CAD
#
# Copyright (c) 2004-2026 United States Government as represented by
# the U.S. Army Research Laboratory.
#
# Redistribution and use in source and binary forms, with or without
# modification, are permitted provided that the following conditions
# are met:
#
# 1. Redistributions of source code must retain the above copyright
# notice, this list of conditions and the following disclaimer.
#
# 2. Redistributions in binary form must reproduce the above
# copyright notice, this list of conditions and the following
# disclaimer in the documentation and/or other materials provided
# with the distribution.
#
# 3. The name of the author may not be used to endorse or promote
# products derived from this software without specific prior written
# permission.
#
# THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS
# OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
# WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
# DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE
# GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
# INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
# WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
# NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
# SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
#
###
# A Shell script to view the differences of a benchmark run,
# displaying the results in a framebuffer window.
#
# The following environment variables will modify how the view diff
# behaves (in case you're not running from a source distribution, for
# example):
#
# PIX - the directory containing the pix files to be compare
# PIXDIFF - the name of a pix diff tool
# PIXFB - the name of a pix to framebuffer tool (e.g. pix-fb)
#
# Authors -
# Mike Muuss
# Christopher Sean Morrison
#
# @(#)$Header$
# Ensure /bin/sh
export PATH || (echo "This isn't sh."; sh $0 $*; kill $$)
path_to_this="`dirname $0`"
echo Looking for benchmark images ...
# find pix reference image directory if we do not already know where
# it is. PIX environment variable overrides
if test "x${PIX}" = "x" ; then
if test -f "$path_to_this/../pix/sphflake.pix" ; then
echo ...found .pix image files in $path_to_this/../pix
PIX="$path_to_this/../pix"
elif test -f "$path_to_this/sphflake.pix" ; then
echo ...found .pix image files in $path_to_this
PIX="$path_to_this"
elif test -f "$path_to_this/../share/brlcad/pix/sphflake.pix" ; then
echo ...found .pix image files in $path_to_this/../share/brlcad/pix
PIX="$path_to_this/../share/brlcad/pix"
fi
else
echo ...using $PIX from PIX environment variable setting
fi
echo Checking for pixel diff utility...
# find pixel diff utility
# PIXDIFF environment variable overrides
if test "x${PIXDIFF}" = "x" ; then
if test -x $path_to_this/pixdiff ; then
echo ...found $path_to_this/pixdiff
PIXDIFF="$path_to_this/pixdiff"
elif test -x $path_to_this/../src/util/pixdiff ; then
echo ...found $path_to_this/../src/util/pixdiff
PIXDIFF="$path_to_this/../src/util/pixdiff"
else
if test -f "$path_to_this/../src/util/pixdiff.c" ; then
echo ...need to build pixdiff
for compiler in $CC gcc cc ; do
COMPILE="$compiler"
if test "x$COMPILE" = "x" ; then
continue
fi
$COMPILE -o pixdiff "$path_to_this/../src/util/pixdiff.c"
if test "x$?" = "x0" ; then
break
fi
if test -f "pixdiff" ; then
break;
fi
done
if test -f "pixdiff" ; then
echo ...built pixdiff with $COMPILE -o pixdiff pixdiff.c
PIXDIFF="./pixdiff"
fi
fi
fi
else
echo ...using $PIXDIFF from PIXDIFF environment variable setting
fi
echo Checking for pix to framebuffer utility...
# find pix to framebuffer utility
# PIXFB environment variable overrides
if test "x${PIXFB}" = "x" ; then
if test -x $path_to_this/pix-fb ; then
echo ...found $path_to_this/pix-fb
PIXFB="$path_to_this/pix-fb"
elif test -x $path_to_this/../src/fb/pix-fb ; then
echo ...found $path_to_this/../src/fb/pix-fb
PIXFB="$path_to_this/../src/fb/pix-fb"
else
if test -f "$path_to_this/../src/fb/pix-fb.c" ; then
echo ...need to build pix-fb
for compiler in $CC gcc cc ; do
COMPILE="$compiler"
if test "x$COMPILE" = "x" ; then
continue
fi
$COMPILE -o pix-fb "$path_to_this/../src/fb/pix-fb.c"
if test "x$?" = "x0" ; then
break
fi
if test -f "pix-fb" ; then
break;
fi
done
if test -f "pix-fb" ; then
echo ...built pix-fb with $COMPILE -o pix-fb pix-fb.c
PIXFB="./pix-fb"
fi
fi
fi
else
echo ...using $PIXFB from PIXFB environment variable setting
fi
echo +++++ moss.pix
${PIXDIFF} ${PIX}/moss.pix moss.pix | ${PIXFB}
echo +++++ world.pix
${PIXDIFF} ${PIX}/world.pix world.pix | ${PIXFB}
echo +++++ star.pix
${PIXDIFF} ${PIX}/star.pix star.pix | ${PIXFB}
echo +++++ bldg391.pix
${PIXDIFF} ${PIX}/bldg391.pix bldg391.pix | ${PIXFB}
echo +++++ m35.pix
${PIXDIFF} ${PIX}/m35.pix m35.pix | ${PIXFB}
echo +++++ sphflake.pix
${PIXDIFF} ${PIX}/sphflake.pix sphflake.pix | ${PIXFB}
# Local Variables:
# mode: sh
# tab-width: 8
# sh-indentation: 4
# sh-basic-offset: 4
# indent-tabs-mode: t
# End:
# ex: shiftwidth=4 tabstop=8
+26
View File
@@ -0,0 +1,26 @@
/*
* brlman/Cakefile
*
* Note: The file "awf" needs to know where ../awf/Cakefile put the
* pieces (ETCDIR by default).
*/
#include "../Cakefile.defs"
#define PRODUCTS awf brlman
#define SRCDIR brlman
#define FILES /**/
#define SRCSUFF /**/
#define MANSECTION 1
#define STATIC_PRODUCTS PRODUCTS /* Force PRODUCTS into dist */
/*
* There is nothing to compile.
* The "install-prod" rule should install PRODUCTS,
* and "inst-dist" rule shoudl take care of copying to distribution dir.
* Nothing else to do.
*/
all&:
@echo "SRCDIR: all done"
#include "../Cakefile.rules"
Executable
+61
View File
@@ -0,0 +1,61 @@
#! /bin/sh
eval `machinetype.sh -v` # BRL mod: sets $BASEDIR
PATH=/bin:/usr/bin ; export PATH
# AWFLIB is where the pieces live
AWFLIB=${AWFLIB-$BASEDIR/etc} # BRL mod
tmp=/tmp/awp$$ # tempfile for building pass 2
errs=/tmp/awe$$ # error messages (awk can't send to stderr)
case "$1" in
-ms) mac=ms ;;
-man) mac=man ;;
*) echo "$0: must specify -ms or -man" >&2
exit 2
;;
esac
shift
dev="$AWFLIB/dev.$TERM"
if test ! -r $dev
then
dev="$AWFLIB/dev.dumb"
fi
trap "rm -f $tmp $errs ; exit 0" 0 1 2
# build the full, macro-set-dependent, pass-2 awk program
(
sed -n '1,/^#include/p' $AWFLIB/pass2.base
cat $AWFLIB/pass2.$mac
sed -n '/^#include/,$p' $AWFLIB/pass2.base
) >$tmp
# do it
(
echo ".^x $errs"
echo ".^b"
echo ".^# 1 <prolog>"
cat $dev $AWFLIB/common $AWFLIB/mac.$mac
if test " $*" = " "
then
echo ".^# 1 <stdin>"
cat
else
for f
do
echo ".^# 1 $f"
cat $f
done
fi
echo ".^e"
) | awk -f $AWFLIB/pass1 | awk -f $tmp | awk -f $AWFLIB/pass3
# error messages, if any
if test -s $errs
then
cat $errs >&2
exit 1
else
exit 0
fi
Executable
+54
View File
@@ -0,0 +1,54 @@
#!/bin/sh
# B R L M A N
#
# A substitute for the "man" command for those systems that do not
# have NROFF. Henry Spencer's "nroff -man" replacement called AWF
# is used instead.
#
# Michael John Muuss, BRL, 23-June-1991.
# Public Domain, Distribution Unlimited
#
# @(#) $Header$ (BRL)
if test $# -lt 1
then
echo "Usage: $0 command"
echo " To obtain help about that command"
exit 1
fi
# Use MANPAGER, else use PAGER, else use "more" command.
MORE="more -s -f"
if test "$PAGER" != ""
then
MORE="${PAGER}"
fi
if test "${MANPAGER}" != ""
then
MORE="${MANPAGER}"
fi
eval `machinetype.sh -v` # sets $BASEDIR
# Ensure that MANPATH is set and has BRL-CAD materials listed first.
MANPATH=${BASEDIR}/man:${MANPATH}
PATH_ELEMENTS=`echo ${MANPATH} | sed 's/^://
s/:://g
s/:$//
s/:\\.:/:/g
s/:/ /g'`
for PLACE in ${PATH_ELEMENTS}
do
PATTERN="${PLACE}/man?/$1.?"
TRY=`eval echo ${PATTERN}`
if test "${TRY}" != "${PATTERN}"
then
# Found something(s), format it/them
echo ${TRY}
awf -man ${TRY} | ${MORE}
fi
done
exit 0
+43
View File
@@ -0,0 +1,43 @@
.TH BRLMAN 1 BRL/CAD
.SH NAME
brlman \- display manual pages for BRL-CAD software
.SH SYNOPSIS
.B brlman
title
.SH DESCRIPTION
.I Brlman
provides a substitute for the
.I man
command for those systems that do not
have
.I nroff.
Henry Spencer's
.I nroff -man
replacement called
.I awf
is used instead.
.I Brlman
uses the environment variable
.I MANPATH
to determine where to search for the manual pages (
.I /usr/brlcad/man
is the default). The pager used is taken from the environment variable
.I MANPAGER
or, if that is nor set
.I PAGER
is used. The default is to use the
.I more -s -f
command.
.SH "SEE ALSO"
awf(1)
.SH AUTHOR
Michael John Muuss
.SH SOURCE
SECAD/VLD Computing Consortium, Bldg 394
.br
The U. S. Army Ballistic Research Laboratory
.br
Aberdeen Proving Ground, Maryland 21005
.SH "BUG REPORTS"
Reports of bugs or problems should be submitted via electronic
mail to <CAD@ARL.ARMY.MIL>.
+33
View File
@@ -0,0 +1,33 @@
/*
* btclsh/Cakefile
*
*/
#define CONFIGDEFS BTCLSH_CONFIG
#define SRCDIR bwish
#define PRODUCTS btclsh
#if 0
#define STATIC_PRODUCTS btclsh.tcl
#endif
#define SRCSUFF .c
#define MANSECTION 1
#define FILES main input tcl cmd
#include "../Cakefile.defs"
#include "../Cakefile.prog"
#if HAS_TCP
# define COMPLETE_LIBES \
LIBPKG LIBWDB LIBRT LIBBN LIBBU LIBBU_LIBES LIBTERMIO BTCLSH_LIBES LIBES
#else
# define COMPLETE_LIBES \
LIBWDB LIBRT LIBBN LIBBU LIBBU_LIBES LIBTERMIO BTCLSH_LIBES LIBES
#endif
btclsh: OBJ LIBRT_DEP LIBBN_DEP LIBBU_DEP LIBWDB_DEP LIBTCL_DEP
sh ../sh/newvers.sh version "BrlCad Tclsh (BTCLSH)"
CC CFLAGS -c vers.c
CC -o btclsh LDFLAGS OBJ COMPLETE_LIBES vers.o
#include "../Cakefile.rules"
+4
View File
@@ -0,0 +1,4 @@
char version[] = "\
@(#) BRL-CAD Release 6.0 BrlCad Tclsh (BTCLSH)\n\
Mon Apr 1 14:01:17 CST 2002, Compilation 1\n\
root@Mustang:/disk1/brlcad6.0/btclsh\n";
+47
View File
@@ -0,0 +1,47 @@
/*
burst/Cakefile
Author: Gary S. Moss
U. S. Army Ballistic Research Laboratory
Aberdeen Proving Ground
Maryland 21005-5066
$Header$ (BRL)
*/
#define CONFIGDEFS LGT_CONFIG -I. -U_POSIX_SOURCE /*-DDEBUG*/
#define SRCDIR burst
#define PRODUCTS burst
#define SRCSUFF .c
#define MANSECTION 1
#define FILES burst error fb glob grid gridrotate idents paint plot prnt trie ui Hm HmGetc HmGlob Sc
#include "../Cakefile.defs"
#include "../Cakefile.prog"
PRODUCTS: OBJ LIBRT_DEP LIBBN_DEP LIBFB_DEP LIBBU_DEP LIBTERMIO_DEP
CC LDFLAGS -o burst OBJ LIBRT LIBBN LIBBU LIBBU_LIBES LIBTERMIO LIBTERMLIB LIBFB LIBFB_LIBES LIBES -lm
all&: PRODUCTS
test&: ../.burst.MTYPE/burst tfiles/ktank.g
../.burst.MTYPE/burst -b < tfiles/ktank.in
@if test $? -ne 0
then echo "Test failed." ; exit 1
fi
diff tfiles/ktank.burst tfiles/ktank.burst.bak4.0
@if test $? -ne 0
then echo "Test failed." ; exit 1
fi
diff tfiles/ktank.shotlines tfiles/ktank.shotlines.bak4.0
@if test $? -ne 0
then echo "Test failed." ; exit 1
fi
@echo "Tested OK."
untest&:
rm -f tfiles/ktank.burst tfiles.ktank.shotlines tfiles/ktank.plot tfiles/ktank.pix tfiles/ktank.g tfiles/ktank.log
tfiles/ktank.g:
asc2g < ../burst/tfiles/ktank.asc > tfiles/ktank.g
#include "../Cakefile.rules"
+1336
View File
File diff suppressed because it is too large Load Diff

Some files were not shown because too many files have changed in this diff Show More