Compare commits

..

No commits in common. "master" and "8.2.78" have entirely different histories.

985 changed files with 43172 additions and 85459 deletions

View File

@ -1 +0,0 @@
./appimage

View File

@ -1,14 +0,0 @@
#! /usr/bin/env bash
FILE="$(basename $1)"
GIT_DATE="$(git log -n1 --pretty=%ai -- $1)"
GIT_AUTHOR="$(git log -n1 --pretty=%ae -- $1)"
GIT_HASH="$(git log -n1 --pretty=%h -- $1)"
GIT_REV="$(git describe --long --always ${GIT_HASH})"
sed \
-e"s@\\\$Date\\\$@\\\$Date: ${GIT_DATE}\\\$@" \
-e"s|\\\$Author\\\$|\\\$Author: ${GIT_AUTHOR}\\\$|" \
-e"s@\\\$Id\\\$@\\\$Id: ${GIT_REV}\\\$@" \
-e"s@\\\$Revision\\\$@\\\$Revision: ${GIT_REV}\\\$@" \
-e"s|\\\$Header\\\$|\\\$Header: ${FILE} ${GIT_REV} ${GIT_DATE} ${GIT_AUTHOR} \\\$|"

8
.gitattributes vendored
View File

@ -1,8 +0,0 @@
*.c filter=header
*.h filter=header
*.cpp filter=header
*.tcl filter=header
*.scm filter=header
Makefile filter=header
*.gds diff=gds

View File

@ -1,170 +0,0 @@
on:
push:
tags:
- "*"
workflow_dispatch:
name: CI-appimage10
env:
APPIMAGETOOL_DOWNLOAD_URL: https://github.com/AppImage/appimagetool/releases/download/continuous/appimagetool-x86_64.AppImage
jobs:
build_appimage10:
name: Build AppImage EL10
runs-on: ubuntu-latest
permissions:
contents: write # action-gh-release
steps:
- name: Checkout code
uses: actions/checkout@v4
with:
fetch-depth: 149 # enough to cover between tags
#fetch-tags: true # this should work see actions/checkout~issue#1471
- name: Get the version
id: get_version
run: |
git show -s
version=$(cat VERSION) # 8.9.999
version_tstamp=$(git show -s "--format=%cs" | tr -d '-') # YYYYMMDD
version_hash=$(git show -s "--format=%h") # abcdefg
version_num=$(ruby -e "print '$GITHUB_REF'.split('/')[2]") # legacy version method: master
echo "version=${version}"
echo "version_tstamp=${version_tstamp}"
echo "version_hash=${version_hash}"
echo "version_num=${version_num}"
VERSION_NUM="${version}~${version_tstamp}~${version_hash}"
echo "VERSION_NUM=${VERSION_NUM}" >> $GITHUB_ENV
echo "MAGIC_APPIMAGE_OUTPUT_FILENAME=Magic-${VERSION_NUM}-x86_64-EL10.AppImage" >> $GITHUB_ENV
# Is this GHA being run due to a push-on-tag ? if so we make a GitHub release, otherwise we just publish artifact
github_tag=$(echo -n "$GITHUB_REF" | sed -e 's#refs/tags/##') # 8.9.999
echo "github_tag=$github_tag"
if echo -n "$GITHUB_REF" | egrep -q "^refs/tags/" # check prefix
then
if [ -n "$github_tag" ]
then
echo "MY_GITHUB_TAG=${github_tag}" >> $GITHUB_ENV
fi
fi
- name: Build project
run: |
cd appimage/10
make
ln -v Magic-x86_64.AppImage "${MAGIC_APPIMAGE_OUTPUT_FILENAME}"
ls -l *.AppImage
sha256sum *.AppImage
pwd
- name: Create RELEASE-NOTES.txt
run: |
cd appimage/10
# Find the last tag (that does not match the current GITHUB_REF)
echo GITHUB_REF=$GITHUB_REF
echo GITHUB_SHA=$GITHUB_SHA
# GitHub CI is a shallow checkout by default (just the files needed to build)
# but we also want history back to next tag, see fetch-tags/fetch-depth actions/checkout~issue#1471
if [[ "$GITHUB_REF" =~ ^refs/tags/ ]]
then
# remove only if ref of tag (to avoid conflict during fetch)
git update-ref -d $GITHUB_REF
echo git_update_ref_exitstatus=$?
fi
set +e
git fetch --tags --prune --no-recurse-submodules --depth=149 origin +$GITHUB_SHA # fetch-tags: true # is broken
echo git_fetch_exitstatus=$?
git_show_ref=$(git show-ref --hash $GITHUB_REF) # get tagcommit hash
git_show_ref_exitstatus=$?
echo git_show_ref_exitstatus=$git_show_ref_exitstatus
echo git_show_ref=$git_show_ref
git_rev_list=$(git rev-list -n1 $GITHUB_REF) # get commit hash
git_rev_list_exitstatus=$?
echo git_rev_list_exitstatus=$git_rev_list_exitstatus
echo git_rev_list=$git_rev_list
set -e
test "$git_show_ref" = "$GITHUB_SHA" || test "$git_rev_list" = "$GITHUB_SHA" # check we got the ref back (or fail CI)
git_describe=$(git describe --tags $GITHUB_SHA | sed -e 's#\-\([0-9]\+\-g\)#\+\1#') # /-\d+-g/
echo git_describe=$git_describe
# RELEASE-NOTES-EL10.txt
echo "### ${MAGIC_APPIMAGE_OUTPUT_FILENAME} commit ${git_describe}" | sed -e 's#~#\\~#g' > RELEASE-NOTES-EL10.txt
echo "" >> RELEASE-NOTES-EL10.txt
echo "This release is based on EL10 (AlmaLinux10), the AppImage format is designed to run on a wide range of Linux distributions." >> RELEASE-NOTES-EL10.txt
echo "" >> RELEASE-NOTES-EL10.txt
echo "See documentation at https://github.com/${GITHUB_REPOSITORY}/blob/${GITHUB_SHA:0:8}/appimage/10/README.md" >> RELEASE-NOTES-EL10.txt
echo "" >> RELEASE-NOTES-EL10.txt
length_info=$(stat "--format=%s bytes" "${MAGIC_APPIMAGE_OUTPUT_FILENAME}")
sha256_info=$(sha256sum "${MAGIC_APPIMAGE_OUTPUT_FILENAME}" | cut -d ' ' -f1)
echo "| | |" >> RELEASE-NOTES-EL10.txt
echo "| :-------- | :------ |" >> RELEASE-NOTES-EL10.txt
echo "| File Name | ${MAGIC_APPIMAGE_OUTPUT_FILENAME} |" | sed -e 's#~#\\~#g' >> RELEASE-NOTES-EL10.txt
echo "| File Length | ${length_info} |" >> RELEASE-NOTES-EL10.txt
echo "| File SHA256 | ${sha256_info} |" >> RELEASE-NOTES-EL10.txt
echo "" >> RELEASE-NOTES-EL10.txt
# RELEASE-NOTES-CL.txt
set +e # allow this to fail to empty string
git_previous_tag=$(git describe --tags --abbrev=0 $(git rev-list --tags --skip=1 --max-count=1))
echo git_previous_tag=$git_previous_tag
set -e
if [ -n "${git_previous_tag}" ]
then
echo "### Change Log (since previous tag):" > RELEASE-NOTES-CL.txt
echo "\`\`\`" >> RELEASE-NOTES-CL.txt
git log --oneline --no-color --no-decorate "refs/tags/${git_previous_tag}..${GITHUB_REF}" >> RELEASE-NOTES-CL.txt
echo "\`\`\`" >> RELEASE-NOTES-CL.txt
else
echo "### Change Log (last commit only):" > RELEASE-NOTES-CL.txt
echo "\`\`\`" >> RELEASE-NOTES-CL.txt
git log --oneline -n1 --no-color --no-decorate "${GITHUB_REF}" >> RELEASE-NOTES-CL.txt
echo "\`\`\`" >> RELEASE-NOTES-CL.txt
fi
echo "" >> RELEASE-NOTES-CL.txt
#echo "### Build Info:" > RELEASE-NOTES-BI.txt
# FIXME extract package version info and DSO symvers into RELEASE-NOTES.txt
#echo "" >> RELEASE-NOTES-BI.txt
cat RELEASE-NOTES-CL.txt >> RELEASE-NOTES-EL10.txt
cat RELEASE-NOTES-EL10.txt
# RELEASE-NOTES-DOCS.txt
echo "See documentation at https://github.com/${GITHUB_REPOSITORY}/blob/${GITHUB_SHA:0:8}/appimage/7/README.md" >> RELEASE-NOTES-DOCS.txt
echo "See documentation at https://github.com/${GITHUB_REPOSITORY}/blob/${GITHUB_SHA:0:8}/appimage/8/README.md" >> RELEASE-NOTES-DOCS.txt
echo "See documentation at https://github.com/${GITHUB_REPOSITORY}/blob/${GITHUB_SHA:0:8}/appimage/9/README.md" >> RELEASE-NOTES-DOCS.txt
echo "See documentation at https://github.com/${GITHUB_REPOSITORY}/blob/${GITHUB_SHA:0:8}/appimage/10/README.md" >> RELEASE-NOTES-DOCS.txt
# RELEASE-NOTES-GH.txt (this is shared for all AppImage for one tag)
echo "### commit ${git_describe}" | sed -e 's#~#\\~#g' > RELEASE-NOTES-GH.txt
if [[ "$GITHUB_REF" =~ ^refs/tags/ ]]
then
# show tag annotation with tags like before
git tag --cleanup=strip "--format=%(contents)" -n "${GITHUB_REF:10}" | sed -e 's#\([~|]\)#\\\1#g' >> RELEASE-NOTES-GH.txt
fi
echo "" >> RELEASE-NOTES-GH.txt
cat RELEASE-NOTES-DOCS.txt >> RELEASE-NOTES-GH.txt
cat RELEASE-NOTES-CL.txt >> RELEASE-NOTES-GH.txt
# Show in action/artifact output
echo "## RELEASE NOTES" >> $GITHUB_STEP_SUMMARY
echo "" >> $GITHUB_STEP_SUMMARY
cat RELEASE-NOTES-EL10.txt >> $GITHUB_STEP_SUMMARY
- name: Upload Release Asset
if: ${{ env.MY_GITHUB_TAG != '' }} # if: ${{ github.ref_type == 'tag' }}
uses: softprops/action-gh-release@v2
with:
body_path: ${{ github.workspace }}/appimage/10/RELEASE-NOTES-GH.txt
files: |
${{ github.workspace }}/appimage/10/${{env.MAGIC_APPIMAGE_OUTPUT_FILENAME}}
${{ github.workspace }}/appimage/10/RELEASE-NOTES-EL10.txt
- name: Upload Artifact
#if: ${{ env.MY_GITHUB_TAG == '' }} # commented out to always upload
uses: actions/upload-artifact@v4
with:
name: ${{env.MAGIC_APPIMAGE_OUTPUT_FILENAME}}
path: |
${{ github.workspace }}/appimage/10/${{env.MAGIC_APPIMAGE_OUTPUT_FILENAME}}

View File

@ -1,170 +0,0 @@
on:
push:
tags:
- "*"
workflow_dispatch:
name: CI-appimage7
env:
APPIMAGETOOL_DOWNLOAD_URL: https://github.com/AppImage/appimagetool/releases/download/continuous/appimagetool-x86_64.AppImage
jobs:
build_appimage7:
name: Build AppImage EL7
runs-on: ubuntu-latest
permissions:
contents: write # action-gh-release
steps:
- name: Checkout code
uses: actions/checkout@v4
with:
fetch-depth: 149 # enough to cover between tags
#fetch-tags: true # this should work see actions/checkout~issue#1471
- name: Get the version
id: get_version
run: |
git show -s
version=$(cat VERSION) # 8.9.999
version_tstamp=$(git show -s "--format=%cs" | tr -d '-') # YYYYMMDD
version_hash=$(git show -s "--format=%h") # abcdefg
version_num=$(ruby -e "print '$GITHUB_REF'.split('/')[2]") # legacy version method: master
echo "version=${version}"
echo "version_tstamp=${version_tstamp}"
echo "version_hash=${version_hash}"
echo "version_num=${version_num}"
VERSION_NUM="${version}~${version_tstamp}~${version_hash}"
echo "VERSION_NUM=${VERSION_NUM}" >> $GITHUB_ENV
echo "MAGIC_APPIMAGE_OUTPUT_FILENAME=Magic-${VERSION_NUM}-x86_64-EL7.AppImage" >> $GITHUB_ENV
# Is this GHA being run due to a push-on-tag ? if so we make a GitHub release, otherwise we just publish artifact
github_tag=$(echo -n "$GITHUB_REF" | sed -e 's#refs/tags/##') # 8.9.999
echo "github_tag=$github_tag"
if echo -n "$GITHUB_REF" | egrep -q "^refs/tags/" # check prefix
then
if [ -n "$github_tag" ]
then
echo "MY_GITHUB_TAG=${github_tag}" >> $GITHUB_ENV
fi
fi
- name: Build project
run: |
cd appimage/7
make
ln -v Magic-x86_64.AppImage "${MAGIC_APPIMAGE_OUTPUT_FILENAME}"
ls -l *.AppImage
sha256sum *.AppImage
pwd
- name: Create RELEASE-NOTES.txt
run: |
cd appimage/7
# Find the last tag (that does not match the current GITHUB_REF)
echo GITHUB_REF=$GITHUB_REF
echo GITHUB_SHA=$GITHUB_SHA
# GitHub CI is a shallow checkout by default (just the files needed to build)
# but we also want history back to next tag, see fetch-tags/fetch-depth actions/checkout~issue#1471
if [[ "$GITHUB_REF" =~ ^refs/tags/ ]]
then
# remove only if ref of tag (to avoid conflict during fetch)
git update-ref -d $GITHUB_REF
echo git_update_ref_exitstatus=$?
fi
set +e
git fetch --tags --prune --no-recurse-submodules --depth=149 origin +$GITHUB_SHA # fetch-tags: true # is broken
echo git_fetch_exitstatus=$?
git_show_ref=$(git show-ref --hash $GITHUB_REF) # get tagcommit hash
git_show_ref_exitstatus=$?
echo git_show_ref_exitstatus=$git_show_ref_exitstatus
echo git_show_ref=$git_show_ref
git_rev_list=$(git rev-list -n1 $GITHUB_REF) # get commit hash
git_rev_list_exitstatus=$?
echo git_rev_list_exitstatus=$git_rev_list_exitstatus
echo git_rev_list=$git_rev_list
set -e
test "$git_show_ref" = "$GITHUB_SHA" || test "$git_rev_list" = "$GITHUB_SHA" # check we got the ref back (or fail CI)
git_describe=$(git describe --tags $GITHUB_SHA | sed -e 's#\-\([0-9]\+\-g\)#\+\1#') # /-\d+-g/
echo git_describe=$git_describe
# RELEASE-NOTES-EL7.txt
echo "### ${MAGIC_APPIMAGE_OUTPUT_FILENAME} commit ${git_describe}" | sed -e 's#~#\\~#g' > RELEASE-NOTES-EL7.txt
echo "" >> RELEASE-NOTES-EL7.txt
echo "This release is based on EL7 (CentOS7), the AppImage format is designed to run on a wide range of Linux distributions." >> RELEASE-NOTES-EL7.txt
echo "" >> RELEASE-NOTES-EL7.txt
echo "See documentation at https://github.com/${GITHUB_REPOSITORY}/blob/${GITHUB_SHA:0:8}/appimage/7/README.md" >> RELEASE-NOTES-EL7.txt
echo "" >> RELEASE-NOTES-EL7.txt
length_info=$(stat "--format=%s bytes" "${MAGIC_APPIMAGE_OUTPUT_FILENAME}")
sha256_info=$(sha256sum "${MAGIC_APPIMAGE_OUTPUT_FILENAME}" | cut -d ' ' -f1)
echo "| | |" >> RELEASE-NOTES-EL7.txt
echo "| :-------- | :------ |" >> RELEASE-NOTES-EL7.txt
echo "| File Name | ${MAGIC_APPIMAGE_OUTPUT_FILENAME} |" | sed -e 's#~#\\~#g' >> RELEASE-NOTES-EL7.txt
echo "| File Length | ${length_info} |" >> RELEASE-NOTES-EL7.txt
echo "| File SHA256 | ${sha256_info} |" >> RELEASE-NOTES-EL7.txt
echo "" >> RELEASE-NOTES-EL7.txt
# RELEASE-NOTES-CL.txt
set +e # allow this to fail to empty string
git_previous_tag=$(git describe --tags --abbrev=0 $(git rev-list --tags --skip=1 --max-count=1))
echo git_previous_tag=$git_previous_tag
set -e
if [ -n "${git_previous_tag}" ]
then
echo "### Change Log (since previous tag):" > RELEASE-NOTES-CL.txt
echo "\`\`\`" >> RELEASE-NOTES-CL.txt
git log --oneline --no-color --no-decorate "refs/tags/${git_previous_tag}..${GITHUB_REF}" >> RELEASE-NOTES-CL.txt
echo "\`\`\`" >> RELEASE-NOTES-CL.txt
else
echo "### Change Log (last commit only):" > RELEASE-NOTES-CL.txt
echo "\`\`\`" >> RELEASE-NOTES-CL.txt
git log --oneline -n1 --no-color --no-decorate "${GITHUB_REF}" >> RELEASE-NOTES-CL.txt
echo "\`\`\`" >> RELEASE-NOTES-CL.txt
fi
echo "" >> RELEASE-NOTES-CL.txt
#echo "### Build Info:" > RELEASE-NOTES-BI.txt
# FIXME extract package version info and DSO symvers into RELEASE-NOTES.txt
#echo "" >> RELEASE-NOTES-BI.txt
cat RELEASE-NOTES-CL.txt >> RELEASE-NOTES-EL7.txt
cat RELEASE-NOTES-EL7.txt
# RELEASE-NOTES-DOCS.txt
echo "See documentation at https://github.com/${GITHUB_REPOSITORY}/blob/${GITHUB_SHA:0:8}/appimage/7/README.md" >> RELEASE-NOTES-DOCS.txt
echo "See documentation at https://github.com/${GITHUB_REPOSITORY}/blob/${GITHUB_SHA:0:8}/appimage/8/README.md" >> RELEASE-NOTES-DOCS.txt
echo "See documentation at https://github.com/${GITHUB_REPOSITORY}/blob/${GITHUB_SHA:0:8}/appimage/9/README.md" >> RELEASE-NOTES-DOCS.txt
echo "See documentation at https://github.com/${GITHUB_REPOSITORY}/blob/${GITHUB_SHA:0:8}/appimage/10/README.md" >> RELEASE-NOTES-DOCS.txt
# RELEASE-NOTES-GH.txt (this is shared for all AppImage for one tag)
echo "### commit ${git_describe}" | sed -e 's#~#\\~#g' > RELEASE-NOTES-GH.txt
if [[ "$GITHUB_REF" =~ ^refs/tags/ ]]
then
# show tag annotation with tags like before
git tag --cleanup=strip "--format=%(contents)" -n "${GITHUB_REF:10}" | sed -e 's#\([~|]\)#\\\1#g' >> RELEASE-NOTES-GH.txt
fi
echo "" >> RELEASE-NOTES-GH.txt
cat RELEASE-NOTES-DOCS.txt >> RELEASE-NOTES-GH.txt
cat RELEASE-NOTES-CL.txt >> RELEASE-NOTES-GH.txt
# Show in action/artifact output
echo "## RELEASE NOTES" >> $GITHUB_STEP_SUMMARY
echo "" >> $GITHUB_STEP_SUMMARY
cat RELEASE-NOTES-EL7.txt >> $GITHUB_STEP_SUMMARY
- name: Upload Release Asset
if: ${{ env.MY_GITHUB_TAG != '' }} # if: ${{ github.ref_type == 'tag' }}
uses: softprops/action-gh-release@v2
with:
body_path: ${{ github.workspace }}/appimage/7/RELEASE-NOTES-GH.txt
files: |
${{ github.workspace }}/appimage/7/${{env.MAGIC_APPIMAGE_OUTPUT_FILENAME}}
${{ github.workspace }}/appimage/7/RELEASE-NOTES-EL7.txt
- name: Upload Artifact
#if: ${{ env.MY_GITHUB_TAG == '' }} # commented out to always upload
uses: actions/upload-artifact@v4
with:
name: ${{env.MAGIC_APPIMAGE_OUTPUT_FILENAME}}
path: |
${{ github.workspace }}/appimage/7/${{env.MAGIC_APPIMAGE_OUTPUT_FILENAME}}

View File

@ -1,170 +0,0 @@
on:
push:
tags:
- "*"
workflow_dispatch:
name: CI-appimage8
env:
APPIMAGETOOL_DOWNLOAD_URL: https://github.com/AppImage/appimagetool/releases/download/continuous/appimagetool-x86_64.AppImage
jobs:
build_appimage8:
name: Build AppImage EL8
runs-on: ubuntu-latest
permissions:
contents: write # action-gh-release
steps:
- name: Checkout code
uses: actions/checkout@v4
with:
fetch-depth: 149 # enough to cover between tags
#fetch-tags: true # this should work see actions/checkout~issue#1471
- name: Get the version
id: get_version
run: |
git show -s
version=$(cat VERSION) # 8.9.999
version_tstamp=$(git show -s "--format=%cs" | tr -d '-') # YYYYMMDD
version_hash=$(git show -s "--format=%h") # abcdefg
version_num=$(ruby -e "print '$GITHUB_REF'.split('/')[2]") # legacy version method: master
echo "version=${version}"
echo "version_tstamp=${version_tstamp}"
echo "version_hash=${version_hash}"
echo "version_num=${version_num}"
VERSION_NUM="${version}~${version_tstamp}~${version_hash}"
echo "VERSION_NUM=${VERSION_NUM}" >> $GITHUB_ENV
echo "MAGIC_APPIMAGE_OUTPUT_FILENAME=Magic-${VERSION_NUM}-x86_64-EL8.AppImage" >> $GITHUB_ENV
# Is this GHA being run due to a push-on-tag ? if so we make a GitHub release, otherwise we just publish artifact
github_tag=$(echo -n "$GITHUB_REF" | sed -e 's#refs/tags/##') # 8.9.999
echo "github_tag=$github_tag"
if echo -n "$GITHUB_REF" | egrep -q "^refs/tags/" # check prefix
then
if [ -n "$github_tag" ]
then
echo "MY_GITHUB_TAG=${github_tag}" >> $GITHUB_ENV
fi
fi
- name: Build project
run: |
cd appimage/8
make
ln -v Magic-x86_64.AppImage "${MAGIC_APPIMAGE_OUTPUT_FILENAME}"
ls -l *.AppImage
sha256sum *.AppImage
pwd
- name: Create RELEASE-NOTES.txt
run: |
cd appimage/8
# Find the last tag (that does not match the current GITHUB_REF)
echo GITHUB_REF=$GITHUB_REF
echo GITHUB_SHA=$GITHUB_SHA
# GitHub CI is a shallow checkout by default (just the files needed to build)
# but we also want history back to next tag, see fetch-tags/fetch-depth actions/checkout~issue#1471
if [[ "$GITHUB_REF" =~ ^refs/tags/ ]]
then
# remove only if ref of tag (to avoid conflict during fetch)
git update-ref -d $GITHUB_REF
echo git_update_ref_exitstatus=$?
fi
set +e
git fetch --tags --prune --no-recurse-submodules --depth=149 origin +$GITHUB_SHA # fetch-tags: true # is broken
echo git_fetch_exitstatus=$?
git_show_ref=$(git show-ref --hash $GITHUB_REF) # get tagcommit hash
git_show_ref_exitstatus=$?
echo git_show_ref_exitstatus=$git_show_ref_exitstatus
echo git_show_ref=$git_show_ref
git_rev_list=$(git rev-list -n1 $GITHUB_REF) # get commit hash
git_rev_list_exitstatus=$?
echo git_rev_list_exitstatus=$git_rev_list_exitstatus
echo git_rev_list=$git_rev_list
set -e
test "$git_show_ref" = "$GITHUB_SHA" || test "$git_rev_list" = "$GITHUB_SHA" # check we got the ref back (or fail CI)
git_describe=$(git describe --tags $GITHUB_SHA | sed -e 's#\-\([0-9]\+\-g\)#\+\1#') # /-\d+-g/
echo git_describe=$git_describe
# RELEASE-NOTES-EL8.txt
echo "### ${MAGIC_APPIMAGE_OUTPUT_FILENAME} commit ${git_describe}" | sed -e 's#~#\\~#g' > RELEASE-NOTES-EL8.txt
echo "" >> RELEASE-NOTES-EL8.txt
echo "This release is based on EL8 (AlmaLinux8), the AppImage format is designed to run on a wide range of Linux distributions." >> RELEASE-NOTES-EL8.txt
echo "" >> RELEASE-NOTES-EL8.txt
echo "See documentation at https://github.com/${GITHUB_REPOSITORY}/blob/${GITHUB_SHA:0:8}/appimage/8/README.md" >> RELEASE-NOTES-EL8.txt
echo "" >> RELEASE-NOTES-EL8.txt
length_info=$(stat "--format=%s bytes" "${MAGIC_APPIMAGE_OUTPUT_FILENAME}")
sha256_info=$(sha256sum "${MAGIC_APPIMAGE_OUTPUT_FILENAME}" | cut -d ' ' -f1)
echo "| | |" >> RELEASE-NOTES-EL8.txt
echo "| :-------- | :------ |" >> RELEASE-NOTES-EL8.txt
echo "| File Name | ${MAGIC_APPIMAGE_OUTPUT_FILENAME} |" | sed -e 's#~#\\~#g' >> RELEASE-NOTES-EL8.txt
echo "| File Length | ${length_info} |" >> RELEASE-NOTES-EL8.txt
echo "| File SHA256 | ${sha256_info} |" >> RELEASE-NOTES-EL8.txt
echo "" >> RELEASE-NOTES-EL8.txt
# RELEASE-NOTES-CL.txt
set +e # allow this to fail to empty string
git_previous_tag=$(git describe --tags --abbrev=0 $(git rev-list --tags --skip=1 --max-count=1))
echo git_previous_tag=$git_previous_tag
set -e
if [ -n "${git_previous_tag}" ]
then
echo "### Change Log (since previous tag):" > RELEASE-NOTES-CL.txt
echo "\`\`\`" >> RELEASE-NOTES-CL.txt
git log --oneline --no-color --no-decorate "refs/tags/${git_previous_tag}..${GITHUB_REF}" >> RELEASE-NOTES-CL.txt
echo "\`\`\`" >> RELEASE-NOTES-CL.txt
else
echo "### Change Log (last commit only):" > RELEASE-NOTES-CL.txt
echo "\`\`\`" >> RELEASE-NOTES-CL.txt
git log --oneline -n1 --no-color --no-decorate "${GITHUB_REF}" >> RELEASE-NOTES-CL.txt
echo "\`\`\`" >> RELEASE-NOTES-CL.txt
fi
echo "" >> RELEASE-NOTES-CL.txt
#echo "### Build Info:" > RELEASE-NOTES-BI.txt
# FIXME extract package version info and DSO symvers into RELEASE-NOTES.txt
#echo "" >> RELEASE-NOTES-BI.txt
cat RELEASE-NOTES-CL.txt >> RELEASE-NOTES-EL8.txt
cat RELEASE-NOTES-EL8.txt
# RELEASE-NOTES-DOCS.txt
echo "See documentation at https://github.com/${GITHUB_REPOSITORY}/blob/${GITHUB_SHA:0:8}/appimage/7/README.md" >> RELEASE-NOTES-DOCS.txt
echo "See documentation at https://github.com/${GITHUB_REPOSITORY}/blob/${GITHUB_SHA:0:8}/appimage/8/README.md" >> RELEASE-NOTES-DOCS.txt
echo "See documentation at https://github.com/${GITHUB_REPOSITORY}/blob/${GITHUB_SHA:0:8}/appimage/9/README.md" >> RELEASE-NOTES-DOCS.txt
echo "See documentation at https://github.com/${GITHUB_REPOSITORY}/blob/${GITHUB_SHA:0:8}/appimage/10/README.md" >> RELEASE-NOTES-DOCS.txt
# RELEASE-NOTES-GH.txt (this is shared for all AppImage for one tag)
echo "### commit ${git_describe}" | sed -e 's#~#\\~#g' > RELEASE-NOTES-GH.txt
if [[ "$GITHUB_REF" =~ ^refs/tags/ ]]
then
# show tag annotation with tags like before
git tag --cleanup=strip "--format=%(contents)" -n "${GITHUB_REF:10}" | sed -e 's#\([~|]\)#\\\1#g' >> RELEASE-NOTES-GH.txt
fi
echo "" >> RELEASE-NOTES-GH.txt
cat RELEASE-NOTES-DOCS.txt >> RELEASE-NOTES-GH.txt
cat RELEASE-NOTES-CL.txt >> RELEASE-NOTES-GH.txt
# Show in action/artifact output
echo "## RELEASE NOTES" >> $GITHUB_STEP_SUMMARY
echo "" >> $GITHUB_STEP_SUMMARY
cat RELEASE-NOTES-EL8.txt >> $GITHUB_STEP_SUMMARY
- name: Upload Release Asset
if: ${{ env.MY_GITHUB_TAG != '' }} # if: ${{ github.ref_type == 'tag' }}
uses: softprops/action-gh-release@v2
with:
body_path: ${{ github.workspace }}/appimage/8/RELEASE-NOTES-GH.txt
files: |
${{ github.workspace }}/appimage/8/${{env.MAGIC_APPIMAGE_OUTPUT_FILENAME}}
${{ github.workspace }}/appimage/8/RELEASE-NOTES-EL8.txt
- name: Upload Artifact
#if: ${{ env.MY_GITHUB_TAG == '' }} # commented out to always upload
uses: actions/upload-artifact@v4
with:
name: ${{env.MAGIC_APPIMAGE_OUTPUT_FILENAME}}
path: |
${{ github.workspace }}/appimage/8/${{env.MAGIC_APPIMAGE_OUTPUT_FILENAME}}

View File

@ -1,170 +0,0 @@
on:
push:
tags:
- "*"
workflow_dispatch:
name: CI-appimage9
env:
APPIMAGETOOL_DOWNLOAD_URL: https://github.com/AppImage/appimagetool/releases/download/continuous/appimagetool-x86_64.AppImage
jobs:
build_appimage9:
name: Build AppImage EL9
runs-on: ubuntu-latest
permissions:
contents: write # action-gh-release
steps:
- name: Checkout code
uses: actions/checkout@v4
with:
fetch-depth: 149 # enough to cover between tags
#fetch-tags: true # this should work see actions/checkout~issue#1471
- name: Get the version
id: get_version
run: |
git show -s
version=$(cat VERSION) # 8.9.999
version_tstamp=$(git show -s "--format=%cs" | tr -d '-') # YYYYMMDD
version_hash=$(git show -s "--format=%h") # abcdefg
version_num=$(ruby -e "print '$GITHUB_REF'.split('/')[2]") # legacy version method: master
echo "version=${version}"
echo "version_tstamp=${version_tstamp}"
echo "version_hash=${version_hash}"
echo "version_num=${version_num}"
VERSION_NUM="${version}~${version_tstamp}~${version_hash}"
echo "VERSION_NUM=${VERSION_NUM}" >> $GITHUB_ENV
echo "MAGIC_APPIMAGE_OUTPUT_FILENAME=Magic-${VERSION_NUM}-x86_64-EL9.AppImage" >> $GITHUB_ENV
# Is this GHA being run due to a push-on-tag ? if so we make a GitHub release, otherwise we just publish artifact
github_tag=$(echo -n "$GITHUB_REF" | sed -e 's#refs/tags/##') # 8.9.999
echo "github_tag=$github_tag"
if echo -n "$GITHUB_REF" | egrep -q "^refs/tags/" # check prefix
then
if [ -n "$github_tag" ]
then
echo "MY_GITHUB_TAG=${github_tag}" >> $GITHUB_ENV
fi
fi
- name: Build project
run: |
cd appimage/9
make
ln -v Magic-x86_64.AppImage "${MAGIC_APPIMAGE_OUTPUT_FILENAME}"
ls -l *.AppImage
sha256sum *.AppImage
pwd
- name: Create RELEASE-NOTES.txt
run: |
cd appimage/9
# Find the last tag (that does not match the current GITHUB_REF)
echo GITHUB_REF=$GITHUB_REF
echo GITHUB_SHA=$GITHUB_SHA
# GitHub CI is a shallow checkout by default (just the files needed to build)
# but we also want history back to next tag, see fetch-tags/fetch-depth actions/checkout~issue#1471
if [[ "$GITHUB_REF" =~ ^refs/tags/ ]]
then
# remove only if ref of tag (to avoid conflict during fetch)
git update-ref -d $GITHUB_REF
echo git_update_ref_exitstatus=$?
fi
set +e
git fetch --tags --prune --no-recurse-submodules --depth=149 origin +$GITHUB_SHA # fetch-tags: true # is broken
echo git_fetch_exitstatus=$?
git_show_ref=$(git show-ref --hash $GITHUB_REF) # get tagcommit hash
git_show_ref_exitstatus=$?
echo git_show_ref_exitstatus=$git_show_ref_exitstatus
echo git_show_ref=$git_show_ref
git_rev_list=$(git rev-list -n1 $GITHUB_REF) # get commit hash
git_rev_list_exitstatus=$?
echo git_rev_list_exitstatus=$git_rev_list_exitstatus
echo git_rev_list=$git_rev_list
set -e
test "$git_show_ref" = "$GITHUB_SHA" || test "$git_rev_list" = "$GITHUB_SHA" # check we got the ref back (or fail CI)
git_describe=$(git describe --tags $GITHUB_SHA | sed -e 's#\-\([0-9]\+\-g\)#\+\1#') # /-\d+-g/
echo git_describe=$git_describe
# RELEASE-NOTES-EL9.txt
echo "### ${MAGIC_APPIMAGE_OUTPUT_FILENAME} commit ${git_describe}" | sed -e 's#~#\\~#g' > RELEASE-NOTES-EL9.txt
echo "" >> RELEASE-NOTES-EL9.txt
echo "This release is based on EL9 (AlmaLinux9), the AppImage format is designed to run on a wide range of Linux distributions." >> RELEASE-NOTES-EL9.txt
echo "" >> RELEASE-NOTES-EL9.txt
echo "See documentation at https://github.com/${GITHUB_REPOSITORY}/blob/${GITHUB_SHA:0:8}/appimage/9/README.md" >> RELEASE-NOTES-EL9.txt
echo "" >> RELEASE-NOTES-EL9.txt
length_info=$(stat "--format=%s bytes" "${MAGIC_APPIMAGE_OUTPUT_FILENAME}")
sha256_info=$(sha256sum "${MAGIC_APPIMAGE_OUTPUT_FILENAME}" | cut -d ' ' -f1)
echo "| | |" >> RELEASE-NOTES-EL9.txt
echo "| :-------- | :------ |" >> RELEASE-NOTES-EL9.txt
echo "| File Name | ${MAGIC_APPIMAGE_OUTPUT_FILENAME} |" | sed -e 's#~#\\~#g' >> RELEASE-NOTES-EL9.txt
echo "| File Length | ${length_info} |" >> RELEASE-NOTES-EL9.txt
echo "| File SHA256 | ${sha256_info} |" >> RELEASE-NOTES-EL9.txt
echo "" >> RELEASE-NOTES-EL9.txt
# RELEASE-NOTES-CL.txt
set +e # allow this to fail to empty string
git_previous_tag=$(git describe --tags --abbrev=0 $(git rev-list --tags --skip=1 --max-count=1))
echo git_previous_tag=$git_previous_tag
set -e
if [ -n "${git_previous_tag}" ]
then
echo "### Change Log (since previous tag):" > RELEASE-NOTES-CL.txt
echo "\`\`\`" >> RELEASE-NOTES-CL.txt
git log --oneline --no-color --no-decorate "refs/tags/${git_previous_tag}..${GITHUB_REF}" >> RELEASE-NOTES-CL.txt
echo "\`\`\`" >> RELEASE-NOTES-CL.txt
else
echo "### Change Log (last commit only):" > RELEASE-NOTES-CL.txt
echo "\`\`\`" >> RELEASE-NOTES-CL.txt
git log --oneline -n1 --no-color --no-decorate "${GITHUB_REF}" >> RELEASE-NOTES-CL.txt
echo "\`\`\`" >> RELEASE-NOTES-CL.txt
fi
echo "" >> RELEASE-NOTES-CL.txt
#echo "### Build Info:" > RELEASE-NOTES-BI.txt
# FIXME extract package version info and DSO symvers into RELEASE-NOTES.txt
#echo "" >> RELEASE-NOTES-BI.txt
cat RELEASE-NOTES-CL.txt >> RELEASE-NOTES-EL9.txt
cat RELEASE-NOTES-EL9.txt
# RELEASE-NOTES-DOCS.txt
echo "See documentation at https://github.com/${GITHUB_REPOSITORY}/blob/${GITHUB_SHA:0:8}/appimage/7/README.md" >> RELEASE-NOTES-DOCS.txt
echo "See documentation at https://github.com/${GITHUB_REPOSITORY}/blob/${GITHUB_SHA:0:8}/appimage/8/README.md" >> RELEASE-NOTES-DOCS.txt
echo "See documentation at https://github.com/${GITHUB_REPOSITORY}/blob/${GITHUB_SHA:0:8}/appimage/9/README.md" >> RELEASE-NOTES-DOCS.txt
echo "See documentation at https://github.com/${GITHUB_REPOSITORY}/blob/${GITHUB_SHA:0:8}/appimage/10/README.md" >> RELEASE-NOTES-DOCS.txt
# RELEASE-NOTES-GH.txt (this is shared for all AppImage for one tag)
echo "### commit ${git_describe}" | sed -e 's#~#\\~#g' > RELEASE-NOTES-GH.txt
if [[ "$GITHUB_REF" =~ ^refs/tags/ ]]
then
# show tag annotation with tags like before
git tag --cleanup=strip "--format=%(contents)" -n "${GITHUB_REF:10}" | sed -e 's#\([~|]\)#\\\1#g' >> RELEASE-NOTES-GH.txt
fi
echo "" >> RELEASE-NOTES-GH.txt
cat RELEASE-NOTES-DOCS.txt >> RELEASE-NOTES-GH.txt
cat RELEASE-NOTES-CL.txt >> RELEASE-NOTES-GH.txt
# Show in action/artifact output
echo "## RELEASE NOTES" >> $GITHUB_STEP_SUMMARY
echo "" >> $GITHUB_STEP_SUMMARY
cat RELEASE-NOTES-EL9.txt >> $GITHUB_STEP_SUMMARY
- name: Upload Release Asset
if: ${{ env.MY_GITHUB_TAG != '' }} # if: ${{ github.ref_type == 'tag' }}
uses: softprops/action-gh-release@v2
with:
body_path: ${{ github.workspace }}/appimage/9/RELEASE-NOTES-GH.txt
files: |
${{ github.workspace }}/appimage/9/${{env.MAGIC_APPIMAGE_OUTPUT_FILENAME}}
${{ github.workspace }}/appimage/9/RELEASE-NOTES-EL9.txt
- name: Upload Artifact
#if: ${{ env.MY_GITHUB_TAG == '' }} # commented out to always upload
uses: actions/upload-artifact@v4
with:
name: ${{env.MAGIC_APPIMAGE_OUTPUT_FILENAME}}
path: |
${{ github.workspace }}/appimage/9/${{env.MAGIC_APPIMAGE_OUTPUT_FILENAME}}

View File

@ -1,289 +0,0 @@
name: CI-canary-matrix
on:
push:
tags:
- "*"
workflow_dispatch:
jobs:
canary:
strategy:
max-parallel: 3
matrix:
os: [ubuntu-24.04, ubuntu-22.04]
# Configure Options
# X11 OGL CAIRO
pkgs: [all, none, no_tk_tcl_rl, no_tk_tcl_brl, no_zlib, no_gc_gl_gu, no_gc, no_gl_gu]
# Toolchain
# ubuntu-20.04 [gcc-9, clang-10]
# ubuntu-22.04 [gcc-11, clang-14]
# ubuntu-24.04 [gcc-13, clang-18]
tc: [default, gcc-10, gcc-11, gcc-12, gcc-13, gcc-14, clang-14, clang-15, clang-17, clang-18, clang-19]
exclude:
- os: ubuntu-22.04
tc: gcc-13
- os: ubuntu-22.04
tc: gcc-14
- os: ubuntu-22.04
tc: clang-17
- os: ubuntu-22.04 # some sources show this as present but not found
tc: clang-18
- os: ubuntu-22.04
tc: clang-19
- os: ubuntu-24.04
tc: gcc-10
- os: ubuntu-24.04
tc: gcc-11
- os: ubuntu-24.04
tc: clang-14
- os: ubuntu-24.04
tc: clang-15
fail-fast: false
runs-on: ${{ matrix.os }}
steps:
- name: Checkout
uses: actions/checkout@v4
- name: Matrix Check
env:
MATRIX_OS: ${{ matrix.os }}
MATRIX_PKGS: ${{ matrix.pkgs }}
MATRIX_TC: ${{ matrix.tc }}
run: |
# This takes the macros params ENV and processes into options list
if [ "${MATRIX_PKGS}" = "none" ]
then
pkgs=""
cfgs=""
else
pkgs="kcnrzCLUX"
cfgs=""
fi
# z no.*_zl zlib1g-dev
# n no.*_nc libncurses-dev
# r no.*_rl libreadline-dev
# R no.*_brl --enable-readline-bundled
# c no.*_tcl tcl-dev
# k no.*_tk tk-dev
# C no.*_gc libcairo-dev
# L no.*_gl libgl-dev
# U no.*_gu libglu1-mesa-dev # GLU requires GL
# X no.*_gx libx11-dev
if echo -n "$MATRIX_PKGS" | grep -q "^no.*_zl"; then
pkgs=$(echo -n "$pkgs" | sed -e 's#z##'); fi
if echo -n "$MATRIX_PKGS" | grep -q "^no.*_nc"; then
pkgs=$(echo -n "$pkgs" | sed -e 's#n##'); fi
if echo -n "$MATRIX_PKGS" | grep -q "^no.*_brl"; then
pkgs=$(echo -n "$pkgs" | sed -e 's#r#R#'); fi # replace
if echo -n "$MATRIX_PKGS" | grep -q "^no.*_rl"; then
pkgs=$(echo -n "$pkgs" | sed -e 's#r##'); fi
if echo -n "$MATRIX_PKGS" | grep -q "^no.*_tcl"; then
pkgs=$(echo -n "$pkgs" | sed -e 's#c##'); fi
if echo -n "$MATRIX_PKGS" | grep -q "^no.*_tk"; then
pkgs=$(echo -n "$pkgs" | sed -e 's#k##'); fi
if echo -n "$MATRIX_PKGS" | grep -q "^no.*_gc"; then
pkgs=$(echo -n "$pkgs" | sed -e 's#C##'); fi
if echo -n "$MATRIX_PKGS" | grep -q "^no.*_gl"; then
pkgs=$(echo -n "$pkgs" | sed -e 's#L##'); fi
if echo -n "$MATRIX_PKGS" | grep -q "^no.*_gu"; then
pkgs=$(echo -n "$pkgs" | sed -e 's#U##'); fi
if echo -n "$MATRIX_PKGS" | grep -q "^no.*_gx"; then
pkgs=$(echo -n "$pkgs" | sed -e 's#X##'); fi
_package_list=()
echo -n $pkgs | grep -q "z" && _package_list+=(zlib1g-dev)
echo -n $pkgs | grep -q "n" && _package_list+=(libncurses-dev)
echo -n $pkgs | grep -q "r" && _package_list+=(libreadline-dev)
echo -n $pkgs | grep -q "c" && _package_list+=(tcl-dev)
echo -n $pkgs | grep -q "k" && _package_list+=(tk-dev)
echo -n $pkgs | grep -q "C" && _package_list+=(libcairo-dev)
echo -n $pkgs | grep -q "L" && _package_list+=(libgl-dev)
echo -n $pkgs | grep -q "U" && _package_list+=(libglu1-mesa-dev)
echo -n $pkgs | grep -q "X" && _package_list+=(libx11-dev)
echo "PACKAGE_LIST=${_package_list[*]}" >> $GITHUB_ENV
#
_configure_args=()
if echo -n "$MATRIX_PKGS" | grep -q "^no.*_zl"; then
_configure_args+=(--disable-compression); fi
if echo -n "$MATRIX_PKGS" | grep -q "^no.*_brl"; then
_configure_args+=(--enable-readline-bundled); fi
if echo -n "$MATRIX_PKGS" | grep -q "^no.*_rl"; then
_configure_args+=(--disable-readline); fi
if echo -n "$MATRIX_PKGS" | grep -q "^no.*_tcl"; then
_configure_args+=(--without-tcl); fi
if echo -n "$MATRIX_PKGS" | grep -q "^no.*_tk"; then
_configure_args+=(--without-tk); fi
if echo -n "$MATRIX_PKGS" | grep -q "^no.*_gc"; then
_configure_args+=(--without-cairo); fi
if echo -n "$MATRIX_PKGS" | grep -q "^no.*_gl"; then
_configure_args+=(--without-opengl); fi
echo "CONFIGURE_ARGS=${_configure_args[*]}" >> $GITHUB_ENV
- name: Setup Toolchain
env:
MATRIX_TC: ${{ matrix.tc }}
run: |
# decode settings
BUILD_GCC_VERSION=$( echo -n "$MATRIX_TC" | grep -i "^gcc" | sed -e 's#^gcc\-\?##i')
BUILD_CLANG_VERSION=$(echo -n "$MATRIX_TC" | grep -i "^clang" | sed -e 's#^clang\-\?##i')
echo "BUILD_GCC_VERSION=$BUILD_GCC_VERSION" >> $GITHUB_ENV
echo "BUILD_CLANG_VERSION=$BUILD_CLANG_VERSION" >> $GITHUB_ENV
if [ -n "$BUILD_GCC_VERSION" ]
then
GCCV=$BUILD_GCC_VERSION
# https://github.com/actions/runner-images/blob/main/images/ubuntu/Ubuntu2404-Readme.md
sudo apt-get install gcc-${GCCV} g++-${GCCV} cpp-${GCCV}
gcc-${GCCV} -v
g++-${GCCV} -v
cpp-${GCCV} -v < /dev/null
ls -l /usr/bin/g++ /usr/bin/g++-[0-9]* /usr/bin/gcc /usr/bin/gcc-[0-9]* /usr/bin/cpp-* /usr/bin/*-gnu-cpp* || true
update-alternatives --list gcc || true
update-alternatives --list g++ || true
update-alternatives --list cpp || true
update-alternatives --query gcc || true
update-alternatives --query g++ || true
update-alternatives --query cpp || true
ls -l /usr/bin/g++ /usr/bin/g++-[0-9]* /usr/bin/gcc /usr/bin/gcc-[0-9]* /usr/bin/cpp-* /usr/bin/*-gnu-cpp* || true
sudo update-alternatives --install /usr/bin/gcc gcc /usr/bin/gcc-${GCCV} 50
sudo update-alternatives --install /usr/bin/g++ g++ /usr/bin/g++-${GCCV} 50
sudo update-alternatives --install "/usr/bin/$(uname -m)-linux-gnu-cpp" cpp "/usr/bin/$(uname -m)-linux-gnu-cpp-${GCCV}" 50
ls -l /usr/bin/g++ /usr/bin/g++-[0-9]* /usr/bin/gcc /usr/bin/gcc-[0-9]* /usr/bin/cpp-* /usr/bin/*-gnu-cpp* || true
update-alternatives --list gcc || true
update-alternatives --list g++ || true
update-alternatives --list cpp || true
hash -r
gcc -v
elif [ -n "$BUILD_CLANG_VERSION" ]
then
CLANGV=$BUILD_CLANG_VERSION
# https://github.com/actions/runner-images/blob/main/images/ubuntu/Ubuntu2404-Readme.md
sudo apt-get install clang-${CLANGV} clang++-${CLANGV} #clang-cpp-${CLANGV}
clang-${CLANGV} -v
clang++-${CLANGV} -v
clang-cpp-${CLANGV} -v < /dev/null
ls -l /usr/bin/clang++ /usr/bin/clang++-[0-9]* /usr/bin/clang /usr/bin/clang-[0-9]* /usr/bin/clang-cpp-* /usr/bin/clang-cpp* || true
update-alternatives --list clang || true
update-alternatives --list clang++ || true
update-alternatives --list clang-cpp || true
update-alternatives --query clang || true
update-alternatives --query clang++ || true
update-alternatives --query clang-cpp || true
ls -l /usr/bin/clang++ /usr/bin/clang++-[0-9]* /usr/bin/clang /usr/bin/clang-[0-9]* /usr/bin/clang-cpp-* /usr/bin/clang-cpp* || true
sudo update-alternatives --install /usr/bin/clang clang /usr/bin/clang-${CLANGV} 50
sudo update-alternatives --install /usr/bin/clang++ clang++ /usr/bin/clang++-${CLANGV} 50
sudo update-alternatives --install "/usr/bin/clang-cpp" clang-cpp "/usr/bin/clang-cpp-${CLANGV}" 50
ls -l /usr/bin/clang++ /usr/bin/clang++-[0-9]* /usr/bin/clang /usr/bin/clang-[0-9]* /usr/bin/clang-cpp-* /usr/bin/clang-cpp* || true
update-alternatives --list clang || true
update-alternatives --list clang++ || true
update-alternatives --list clang-cpp || true
hash -r
clang -v
fi
- name: Get Dependencies
run: |
if [ -n "$PACKAGE_LIST" ]
then
sudo apt-get install -y ${PACKAGE_LIST}
fi
- name: Build
run: |
if [ -n "$BUILD_CLANG_VERSION" ]
then
export CC="clang-${BUILD_CLANG_VERSION}"
export CXX="clang++-${BUILD_CLANG_VERSION}"
export CPP="clang-cpp-${BUILD_CLANG_VERSION}"
fi
set -o pipefail # due to pipe inside CI
./configure $CONFIGURE_ARGS 2>&1 | tee CONFIGURE.LOG
egrep "^(CPP|CXX|CC)\s" defs.mak
# Add -Wall for CI loggings
sed -e 's# -Werror=# -Wall -Werror=#' -i defs.mak
# Non security/reliability related warnings
#sed -e 's# -Werror=# -Wno-unused-variable -Werror=#' -i defs.mak
#sed -e 's# -Werror=# -Wno-unused-local-typedefs -Werror=#' -i defs.mak
#sed -e 's# -Werror=# -Wno-unused-label -Werror=#' -i defs.mak
#sed -e 's# -Werror=# -Wno-unused-but-set-variable -Werror=#' -i defs.mak
make database/database.h
make -j$(nproc) 2>&1 | tee MAKE.LOG
- name: Summary
env:
MATRIX_OS: ${{ matrix.os }}
MATRIX_PKGS: ${{ matrix.pkgs }}
run: |
set +e
grep "error:" MAKE.LOG > MAKE_error.LOG
grep "warning:" MAKE.LOG > MAKE_warning.LOG
# Less important warnings relating to codesmell more than security (filter out of headline)
grep -v "Wunused-variable" MAKE_warning.LOG |
grep -v "Wunused-local-typedefs" |
grep -v "Wunused-label" |
grep -v "Wunused-but-set-variable" > MAKE_warning_filtered.LOG
ls -l
wc -l *.LOG
error_count=$( grep -c "error:" MAKE_error.LOG)
filtered_warning_count=$(grep -c "warning:" MAKE_warning_filtered.LOG)
title="### $(cat VERSION) ${MATRIX_OS} ${MATRIX_TC} ${MATRIX_PKGS} :: "
if [ "$error_count" -gt 0 ]
then
title="$title $error_count error(s)"
fi
if [ "$filtered_warning_count" -gt 0 ]
then
title="$title $filtered_warning_count warning(s)"
fi
(
total_error_count=$( wc -l MAKE_error.LOG | cut -d' ' -f1)
total_warning_count=$(wc -l MAKE_warning.LOG | cut -d' ' -f1)
echo "$title"
echo ""
echo "PACKAGE_LIST=$PACKAGE_LIST"
echo "CONFIGURE_ARGS=$CONFIGURE_ARGS"
echo ""
if [ "$BUILD_CLANG_VERSION" ]
then
"clang-${BUILD_CLANG_VERSION}" --version | head -n1
if ! update-alternatives --list clang
then
update-alternatives --list "clang-${BUILD_CLANG_VERSION}"
fi
else
gcc --version | head -n1
if ! update-alternatives --list gcc
then
update-alternatives --list "gcc-${BUILD_GCC_VERSION}"
fi
fi
echo ""
echo "total ${total_error_count} error(s) ${total_warning_count} warning(s) :"
echo "|Count|Warning Group (-j build log inaccuracies)|"
echo "|--:|:--|"
# due to -j build the log lines might get corrupted, so missing/incorrect/bogus entries might be seen
# so we add extra: egrep "\[\-W.*\]" (to try to remove that)
sed -e 's#.*\(\[\-W\)#\1#' -e 's#\(\]\).*$#\1#' MAKE_warning.LOG | egrep "\[\-W.*\]" | sort | uniq -c | sort -n | tr -s ' ' | tr ' ' '|' | awk '{print $0"|"}'
echo ""
sed -e '0,/Configuration Summary/d' -e '/\---/,//d' CONFIGURE.LOG | egrep "^.*:"
echo ""
grep DCAD_DIR MAKE.LOG | tail -n1
) >> $GITHUB_STEP_SUMMARY

View File

@ -1,49 +0,0 @@
# This is a basic workflow to help you get started with Actions
name: CI-aarch64
# Controls when the workflow will run
on:
push:
pull_request:
workflow_dispatch:
# A workflow run is made up of one or more jobs that can run sequentially or in parallel
jobs:
simple_build_linux_arm:
runs-on: ubuntu-24.04-arm
steps:
- uses: actions/checkout@v4
- name: Get Dependencies
run: |
sudo apt-get update
sudo apt-get install -y tcl-dev tk-dev libcairo-dev
- name: Build
run: |
./configure
make database/database.h
make -j$(nproc)
simple_build_wasm_arm:
runs-on: ubuntu-24.04-arm
steps:
- uses: actions/checkout@v4
- name: Get Dependencies
run: |
git clone https://github.com/emscripten-core/emsdk.git
cd emsdk
./emsdk install latest
./emsdk activate latest
- name: Build
run: |
source ./emsdk/emsdk_env.sh
emconfigure ./configure --without-cairo --without-opengl --without-x --disable-readline --disable-compression --target=asmjs-unknown-emscripten
echo "===== defs.mak ====="
cat defs.mak
echo "===== defs.mak ====="
emmake make
- name: archive wasm bundle
uses: actions/upload-artifact@v4
with:
name: magic-wasm-bundle-arm
path: |
${{ github.workspace }}/magic/magic.wasm

View File

@ -1,475 +0,0 @@
# This is a basic workflow to help you get started with Actions
name: CI-macos
# Controls when the workflow will run
on:
push:
pull_request:
workflow_dispatch:
# A workflow run is made up of one or more jobs that can run sequentially or in parallel
jobs:
simple_build_macos15:
runs-on: macos-15-intel # only and last supported intel MacOS
timeout-minutes: 45 # x86_64 seems non-SSD based (slower)
steps:
- name: Checkout
uses: actions/checkout@v4
- name: Get Dependencies
shell: bash # default shell has unwanted broken pipe indication
run: |
brew install --cask xquartz
PACKAGE_LIST="xquartz"
brew install cairo tcl-tk@8 tcsh gnu-sed
_package_list="cairo tcl-tk@8 tcsh gnu-sed"
# These seem needed maybe they are being provided from somewhere else GHA runner
# or brew transitive depend either way doesn't hurt to confirm they are installed.
_package_list="$_package_list libglu freeglut"
if [ -n "$PACKAGE_LIST" ]
then
brew install $PACKAGE_LIST
fi
PACKAGE_LIST="$PACKAGE_LIST $_package_list"
echo "PACKAGE_LIST=$PACKAGE_LIST" >> $GITHUB_ENV
echo "UNAME_M=$(uname -m)" >> $GITHUB_ENV
set +e
set +o pipefail # macosx this is on by default (turn it off)
(
echo "### $(uname -s) $(uname -m) $(uname -r)"
echo ""
set +e
set +o pipefail # macosx this is on by default (turn it off)
export HOMEBREW_NO_COLOR=true
export HOMEBREW_NO_EMOKI=true
# output to $TMPFILE first, then head, instead of using pipeline directly
# this removes unwanted GHA SIGPIPE error/warning indicators from GHA logs
# brew maybe a nodejs command which has a known issue in this area on macosx
TMPFILE=/tmp/shell0$$.tmp
brew info xquartz > $TMPFILE && head -n1 $TMPFILE
brew info cairo > $TMPFILE && head -n1 $TMPFILE
brew info libglu > $TMPFILE && head -n1 $TMPFILE
brew info freeglut > $TMPFILE && head -n1 $TMPFILE
brew info tcl-tk > $TMPFILE && head -n1 $TMPFILE
brew info tcl-tk@8 > $TMPFILE && head -n1 $TMPFILE
brew info tcsh > $TMPFILE && head -n1 $TMPFILE
brew info gnu-sed > $TMPFILE && head -n1 $TMPFILE
echo ""
cc -v 2>&1
echo ""
xcodebuild -version
echo ""
xcodebuild -showsdks | grep macOS
) >> $GITHUB_STEP_SUMMARY
- name: Search
run: |
set +e
( # designed to speed up this process in a single scan
echo "#!/bin/sh"
echo "echo \$*"
echo "ls -ld -- \$*"
echo "shasum -a 1 \$* </dev/null"
echo "echo \"\""
echo "exit 0"
) > search.sh
echo "=== search.sh"
cat search.sh
chmod a+x search.sh
find /opt /usr $HOME \( -iname "libX11.*dylib" -or -iname "Xlib.h" -or -iname "libtcl*dylib" -or -iname "tcl.h" \) -exec ./search.sh {} \; 2>/dev/null
#
# Example symbols that were found missing from the tcl-tk X11 implementation
#find /opt /usr $HOME -iname "x*.h" -exec grep -Hn "XCreateGC" {} \; 2>/dev/null || true
#find /opt /usr $HOME -iname "x*.h" -exec grep -Hn "XGetVisualInfo" {} \; 2>/dev/null || true
#for i in /usr/X11/include/X11/Xlib.h /opt/X11/include/X11/Xlib.h /usr/local/include/X11/Xlib.h;
#do
# echo "====== $i"
# head -n 50 "$i"
# echo "==="
# tail -n 50 "$i"
# echo "======"
#done
# Different GHA platforms have different layouts (x86_64/arm64)
echo "=== /opt"
ls -l /opt
if [ -d /opt/homebrew ]
then
echo "=== /opt/homebrew"
ls -l /opt/homebrew
fi
echo "=== /usr/local/opt"
ls -l /usr/local/opt
echo "=== /usr/local/opt/runner"
ls -l /usr/local/opt/runner
echo "Done"
- name: Build
run: |
export PATH="/opt/X11/bin:$PATH"
./scripts/configure_mac 2>&1 | tee CONFIGURE.LOG
config_log=""
if [ -f scripts/config.log ]
then
config_log="scripts/config.log"
elif [ -f build-magic/config.log ]
then
config_log="build-magic/config.log"
fi
if [ -n "$config_log" ]
then
CONFIGURE_ARGS=$(head -n 10 $config_log | egrep "./configure" | sed -e 's#^ *\$ ##' -e 's#./configure ##')
echo "CONFIGURE_ARGS=$CONFIGURE_ARGS" >> $GITHUB_ENV
fi
echo "===== defs.mak ====="
cat defs.mak
echo "===== defs.mak ====="
make database/database.h
make -j$(sysctl -n hw.ncpu) 2>&1 | tee MAKE.LOG
- name: Install
run: |
sudo make install
- name: Kick The Tyres
run: |
set +e
echo "=== ls -l"
ls -l
find . -type f \( -name "*.dylib" -or -name "magic" -or -name "magicexec" -or -name "magicdnull" \)
echo "=== find /usr/local/bin"
find /usr/local/bin -mtime 0
echo "=== find /usr/local/share"
find /usr/local/share -mtime 0
echo "=== find /usr/local/lib/magic"
find /usr/local/lib/magic -mtime 0
echo "=== otool -L magic/tclmagic.dylib"
otool -L magic/tclmagic.dylib
echo "=== otool -L tcltk/magicexec"
otool -L tcltk/magicexec
echo "=== otool -L tcltk/magicdnull"
otool -L tcltk/magicdnull
set +o pipefail # macosx this is on by default (turn it off)
echo "=== magic --version"
magic --version
echo "=== magic -d help -noconsole"
magic -d help -noconsole
echo "=== magic -d null -noconsole -nowindow -T scmos"
echo "version ; quit" | magic -d null -noconsole -nowindow -T scmos
echo "=== magic -d null -noconsole -T scmos"
echo "version ; quit" | magic -d null -noconsole -T scmos
- name: Summary
if: always()
run: |
set +e
ls -l
touch MAKE.LOG # just in case it did not even build
grep "error:" MAKE.LOG > MAKE_error.LOG
grep "warning:" MAKE.LOG > MAKE_warning.LOG
# Less important warnings relating to codesmell more than security (filter out of headline)
grep -v "Wunused-variable" MAKE_warning.LOG |
grep -v "Wunused-local-typedefs" |
grep -v "Wunused-label" |
grep -v "Wunused-but-set-variable" > MAKE_warning_filtered.LOG
wc -l *.LOG
error_count=$( grep -c "error:" MAKE_error.LOG)
filtered_warning_count=$(grep -c "warning:" MAKE_warning_filtered.LOG)
title="### $(cat VERSION) ${MATRIX_OS} ${MATRIX_TC} ${MATRIX_PKGS} :: "
if [ "$error_count" -gt 0 ]
then
title="$title $error_count error(s)"
fi
if [ "$filtered_warning_count" -gt 0 ]
then
title="$title $filtered_warning_count warning(s)"
fi
(
total_error_count=$( wc -l MAKE_error.LOG | cut -d' ' -f1)
total_warning_count=$(wc -l MAKE_warning.LOG | cut -d' ' -f1)
echo "---"
echo "$title"
echo ""
[ -f scripts/config.log ] && grep "./configure" scripts/config.log | head -n1
echo ""
echo "PACKAGE_LIST=$PACKAGE_LIST"
echo "CONFIGURE_ARGS=$CONFIGURE_ARGS"
echo ""
if [ -s MAKE.LOG ]
then
echo "total ${total_error_count} error(s) ${total_warning_count} warning(s) :"
echo "|Count|Warning Group (-j build log inaccuracies)|"
echo "|--:|:--|"
# due to -j build the log lines might get corrupted, so missing/incorrect/bogus entries might be seen
# so we add extra: egrep "\[\-W.*\]" (to try to remove that)
sed -e 's#.*\(\[\-W\)#\1#' -e 's#\(\]\).*$#\1#' MAKE_warning.LOG | egrep "\[\-W.*\]" | sort | uniq -c | sort -n | tr -s ' ' | tr ' ' '|' | awk '{print $0"|"}'
echo ""
fi
grep -A100 "Configuration Summary" CONFIGURE.LOG | grep -v "Configuration Summary" | egrep "^.*:" | sed -e '/\---/,//d'
echo ""
grep DCAD_DIR MAKE.LOG | tail -n1
) >> $GITHUB_STEP_SUMMARY
- name: Prepare archive
run: |
mkdir -p dist
make install "DESTDIR=$(pwd)/dist"
# Diagnostic details about this build
mkdir -p dist/BUILD-INFO
set +e
cp */config.log dist/BUILD-INFO/
cp *.mak dist/BUILD-INFO/
cp *.LOG dist/BUILD-INFO/
- name: Upload archive magic-macos15
uses: actions/upload-artifact@v4
with:
name: magic-macos15
path: |
${{ github.workspace }}/dist
simple_build_macos:
runs-on: macos-latest
timeout-minutes: 30 # arm64 seems SSD based (faster)
steps:
- name: Checkout
uses: actions/checkout@v4
- name: Get Dependencies
shell: bash # default shell has unwanted broken pipe indication
run: |
brew install --cask xquartz
PACKAGE_LIST="xquartz"
brew install cairo tcl-tk@8 tcsh gnu-sed
_package_list="cairo tcl-tk@8 tcsh gnu-sed"
# These seem needed maybe they are being provided from somewhere else GHA runner
# or brew transitive depend either way doesn't hurt to confirm they are installed.
_package_list="$_package_list libglu freeglut"
if [ -n "$PACKAGE_LIST" ]
then
brew install $PACKAGE_LIST
fi
PACKAGE_LIST="$PACKAGE_LIST $_package_list"
echo "PACKAGE_LIST=$PACKAGE_LIST" >> $GITHUB_ENV
echo "UNAME_M=$(uname -m)" >> $GITHUB_ENV
set +e
set +o pipefail # macosx this is on by default (turn it off)
(
echo "### $(uname -s) $(uname -m) $(uname -r)"
echo ""
set +e
set +o pipefail # macosx this is on by default (turn it off)
export HOMEBREW_NO_COLOR=true
export HOMEBREW_NO_EMOKI=true
# output to $TMPFILE first, then head, instead of using pipeline directly
# this removes unwanted GHA SIGPIPE error/warning indicators from GHA logs
# brew maybe a nodejs command which has a known issue in this area on macosx
TMPFILE=/tmp/shell0$$.tmp
brew info xquartz > $TMPFILE && head -n1 $TMPFILE
brew info cairo > $TMPFILE && head -n1 $TMPFILE
brew info libglu > $TMPFILE && head -n1 $TMPFILE
brew info freeglut > $TMPFILE && head -n1 $TMPFILE
brew info tcl-tk > $TMPFILE && head -n1 $TMPFILE
brew info tcl-tk@8 > $TMPFILE && head -n1 $TMPFILE
brew info tcsh > $TMPFILE && head -n1 $TMPFILE
brew info gnu-sed > $TMPFILE && head -n1 $TMPFILE
echo ""
cc -v 2>&1
echo ""
xcodebuild -version
echo ""
xcodebuild -showsdks | grep macOS
) >> $GITHUB_STEP_SUMMARY
- name: Search
run: |
set +e
( # designed to speed up this process in a single scan
echo "#!/bin/sh"
echo "echo \$*"
echo "ls -ld -- \$*"
echo "shasum -a 1 \$* </dev/null"
echo "echo \"\""
echo "exit 0"
) > search.sh
echo "=== search.sh"
cat search.sh
chmod a+x search.sh
find /opt /usr $HOME \( -iname "libX11.*dylib" -or -iname "Xlib.h" -or -iname "libtcl*dylib" -or -iname "tcl.h" \) -exec ./search.sh {} \; 2>/dev/null
#
# Example symbols that were found missing from the tcl-tk X11 implementation
#find /opt /usr $HOME -iname "x*.h" -exec grep -Hn "XCreateGC" {} \; 2>/dev/null || true
#find /opt /usr $HOME -iname "x*.h" -exec grep -Hn "XGetVisualInfo" {} \; 2>/dev/null || true
#for i in /usr/X11/include/X11/Xlib.h /opt/X11/include/X11/Xlib.h /usr/local/include/X11/Xlib.h;
#do
# echo "====== $i"
# head -n 50 "$i"
# echo "==="
# tail -n 50 "$i"
# echo "======"
#done
# Different GHA platforms have different layouts (x86_64/arm64)
echo "=== /opt"
ls -l /opt
if [ -d /opt/homebrew ]
then
echo "=== /opt/homebrew"
ls -l /opt/homebrew
fi
echo "=== /usr/local/opt"
ls -l /usr/local/opt
echo "=== /usr/local/opt/runner"
ls -l /usr/local/opt/runner
echo "Done"
- name: Build
run: |
export PATH="/opt/X11/bin:$PATH"
./scripts/configure_mac 2>&1 | tee CONFIGURE.LOG
config_log=""
if [ -f scripts/config.log ]
then
config_log="scripts/config.log"
elif [ -f build-magic/config.log ]
then
config_log="build-magic/config.log"
fi
if [ -n "$config_log" ]
then
CONFIGURE_ARGS=$(head -n 10 $config_log | egrep "./configure" | sed -e 's#^ *\$ ##' -e 's#./configure ##')
echo "CONFIGURE_ARGS=$CONFIGURE_ARGS" >> $GITHUB_ENV
fi
echo "===== defs.mak ====="
cat defs.mak
echo "===== defs.mak ====="
make database/database.h
make -j$(sysctl -n hw.ncpu) 2>&1 | tee MAKE.LOG
- name: Install
run: |
sudo make install
- name: Kick The Tyres
run: |
set +e
echo "=== ls -l"
ls -l
find . -type f \( -name "*.dylib" -or -name "magic" -or -name "magicexec" -or -name "magicdnull" \)
echo "=== find /usr/local/bin"
find /usr/local/bin -mtime 0
echo "=== find /usr/local/share"
find /usr/local/share -mtime 0
echo "=== find /usr/local/lib/magic"
find /usr/local/lib/magic -mtime 0
echo "=== otool -L magic/tclmagic.dylib"
otool -L magic/tclmagic.dylib
echo "=== otool -L tcltk/magicexec"
otool -L tcltk/magicexec
echo "=== otool -L tcltk/magicdnull"
otool -L tcltk/magicdnull
set +o pipefail # macosx this is on by default (turn it off)
echo "=== magic --version"
magic --version
echo "=== magic -d help -noconsole"
magic -d help -noconsole
echo "=== magic -d null -noconsole -nowindow -T scmos"
echo "version ; quit" | magic -d null -noconsole -nowindow -T scmos
echo "=== magic -d null -noconsole -T scmos"
echo "version ; quit" | magic -d null -noconsole -T scmos
- name: Summary
if: always()
run: |
set +e
ls -l
touch MAKE.LOG # just in case it did not even build
grep "error:" MAKE.LOG > MAKE_error.LOG
grep "warning:" MAKE.LOG > MAKE_warning.LOG
# Less important warnings relating to codesmell more than security (filter out of headline)
grep -v "Wunused-variable" MAKE_warning.LOG |
grep -v "Wunused-local-typedefs" |
grep -v "Wunused-label" |
grep -v "Wunused-but-set-variable" > MAKE_warning_filtered.LOG
wc -l *.LOG
error_count=$( grep -c "error:" MAKE_error.LOG)
filtered_warning_count=$(grep -c "warning:" MAKE_warning_filtered.LOG)
title="### $(cat VERSION) ${MATRIX_OS} ${MATRIX_TC} ${MATRIX_PKGS} :: "
if [ "$error_count" -gt 0 ]
then
title="$title $error_count error(s)"
fi
if [ "$filtered_warning_count" -gt 0 ]
then
title="$title $filtered_warning_count warning(s)"
fi
(
total_error_count=$( wc -l MAKE_error.LOG | cut -d' ' -f1)
total_warning_count=$(wc -l MAKE_warning.LOG | cut -d' ' -f1)
echo "---"
echo "$title"
echo ""
[ -f scripts/config.log ] && grep "./configure" scripts/config.log | head -n1
echo ""
echo "PACKAGE_LIST=$PACKAGE_LIST"
echo "CONFIGURE_ARGS=$CONFIGURE_ARGS"
echo ""
if [ -s MAKE.LOG ]
then
echo "total ${total_error_count} error(s) ${total_warning_count} warning(s) :"
echo "|Count|Warning Group (-j build log inaccuracies)|"
echo "|--:|:--|"
# due to -j build the log lines might get corrupted, so missing/incorrect/bogus entries might be seen
# so we add extra: egrep "\[\-W.*\]" (to try to remove that)
sed -e 's#.*\(\[\-W\)#\1#' -e 's#\(\]\).*$#\1#' MAKE_warning.LOG | egrep "\[\-W.*\]" | sort | uniq -c | sort -n | tr -s ' ' | tr ' ' '|' | awk '{print $0"|"}'
echo ""
fi
grep -A100 "Configuration Summary" CONFIGURE.LOG | grep -v "Configuration Summary" | egrep "^.*:" | sed -e '/\---/,//d'
echo ""
grep DCAD_DIR MAKE.LOG | tail -n1
) >> $GITHUB_STEP_SUMMARY
- name: Prepare archive
run: |
mkdir -p dist
make install "DESTDIR=$(pwd)/dist"
# Diagnostic details about this build
mkdir -p dist/BUILD-INFO
set +e
cp */config.log dist/BUILD-INFO/
cp *.mak dist/BUILD-INFO/
cp *.LOG dist/BUILD-INFO/
- name: Upload archive magic-macos
uses: actions/upload-artifact@v4
with:
name: magic-macos
path: |
${{ github.workspace }}/dist

View File

@ -1,61 +0,0 @@
# This is a basic workflow to help you get started with Actions
name: CI
# Controls when the workflow will run
on:
push:
pull_request:
workflow_dispatch:
# A workflow run is made up of one or more jobs that can run sequentially or in parallel
jobs:
vezzal:
# The type of runner that the job will run on
runs-on: ubuntu-latest
# Steps represent a sequence of tasks that will be executed as part of the job
steps:
- name: Pulling the docker image
run: docker pull vezzal/vezzal:v1
- name: Start the container with the docker image
run: docker run -id --name test_magic vezzal/vezzal:v1 bash | exit
- name: Run the testing on the container and send the mail
run: docker exec test_magic /vezzal/test_magic.sh "lankasaicharan123@gmail.com,tim@opencircuitdesign.com" ${{secrets.MAILING_KEY}}
simple_build_linux:
runs-on: ubuntu-22.04
steps:
- uses: actions/checkout@v4
- name: Get Dependencies
run: |
sudo apt-get install -y tcl-dev tk-dev libcairo-dev
- name: Build
run: |
./configure
make database/database.h
make -j$(nproc)
simple_build_wasm:
runs-on: ubuntu-22.04
steps:
- uses: actions/checkout@v4
- name: Get Dependencies
run: |
git clone https://github.com/emscripten-core/emsdk.git
cd emsdk
./emsdk install latest
./emsdk activate latest
- name: Build
run: |
source ./emsdk/emsdk_env.sh
emconfigure ./configure --without-cairo --without-opengl --without-x --disable-readline --disable-compression --target=asmjs-unknown-emscripten
echo "===== defs.mak ====="
cat defs.mak
echo "===== defs.mak ====="
emmake make
- name: archive wasm bundle
uses: actions/upload-artifact@v4
with:
name: magic-wasm-bundle
path: |
${{ github.workspace }}/magic/magic.wasm

26
.gitignore vendored
View File

@ -1,5 +1,5 @@
defs.mak
*/Depend
Depend
config.cache
config.log
scripts/config.log
@ -10,25 +10,5 @@ scripts/defs.mak
*.so
*~
scmos/cif_template/objs/*
database/database.h
install.log
magic/proto.magicrc
make.log
scmos/gdsquery.tech
scmos/minimum.tech
scmos/scmos-sub.tech
scmos/scmos-tm.tech
scmos/scmos.tech
scmos/scmosWR.tech
scmos/nmos.tech
tcltk/magic.sh
tcltk/magic.tcl
tcltk/magicdnull
tcltk/magicexec
tcltk/ext2spice.sh
tcltk/ext2sim.sh
magic/tclmagic.dylib
tcltk/magicdnull.dSYM/
tcltk/magicexec.dSYM/
reconfigure.sh
pfx/
UPDATE_ME
VERSION

View File

@ -7,8 +7,6 @@ Autoconf Capsule Summary:
make
make install
Note: Remember to use 'gmake' on FreeBSD.
Autoconf options (use "./configure --help" for a complete list):
--prefix=DIR Indicates the install directory. Determines the
@ -47,12 +45,6 @@ Autoconf Capsule Summary:
Disable threaded X11 and OpenGL graphics.
Normally enabled.
--disable-compression
Disable reading and writing of compressed
(gzipped) GDS files and reading of compressed
.mag files. Normally enabled, if the zlib
development package is installed.
Notes to Magic maintainers:
--------------------------

View File

@ -1,79 +0,0 @@
# Installing Magic on macOS (Tested on Big Sur)
## With Brew
Get [Homebrew](https://brew.sh).
```sh
brew install cairo tcl-tk@8 python3 gnu-sed
brew install --cask xquartz
./scripts/configure_mac
# If you have both TCL8 and TCL9 installed you may need to verify which was selected.
make database/database.h
make -j$(sysctl -n hw.ncpu)
make install # may need sudo depending on your setup
```
## Without Brew
Get [XQuartz](https://github.com/XQuartz/XQuartz)
### Build Tcl for X11
We are following the instructions from xschem (https://github.com/StefanSchippers/xschem/blob/master/README_MacOS.md).
* Download Tcl from https://prdownloads.sourceforge.net/tcl/tcl8.6.10-src.tar.gz
We are using not `opt` but `opt2` so that this Tcl does not interfere with `tcl-tk` from HomeBrew.
Extract the Tcl sources and then go to the unix folder and execute the following commands::
```
./configure --prefix=/usr/local/opt2/tcl-tk
make
make install
```
### Build Tk for X11
* Download Tk from https://prdownloads.sourceforge.net/tcl/tk8.6.10-src.tar.gz
Extract Tk source and then go to the unix folder:
NOTE: before running 'make' inspect the Makefile and ensure the LIB_RUNTIME_DIR is set as follows. Make the correction if not:
```
LIB_RUNTIME_DIR = $(libdir)
```
```
./configure --prefix=/usr/local/opt2/tcl-tk \
--with-tcl=/usr/local/opt2/tcl-tk/lib --with-x \
--x-includes=/opt/X11/include --x-libraries=/opt/X11/lib
make
make install
```
### Build magic
We need to provide this `tcl-tk` and suppress compilation errors.
```
./configure --with-tcl=/usr/local/opt2/tcl-tk/lib \
--with-tk=/usr/local/opt2/tcl-tk/lib \
--x-includes=/opt/X11/include \
--x-libraries=/opt/X11/lib \
CFLAGS=-Wno-error=implicit-function-declaration
make
make install
```
## If facing issue with layout window not opening / XQuartz:
Make sure that the output of the following command is ```:0```.
```
echo $DISPLAY
```
if the above command doesn't display ```:0``` then add the following line in ```.zshrc```.
```
export PATH="/opt/X11/bin:$PATH"
```
Close & reopen terminal to load the path. Then set display manually to ```0``` by using the following command.
```
export DISPLAY=:0
```
Now ```echo DISPLAY``` should give ```:0``` as output.

10
LICENSE
View File

@ -1,10 +0,0 @@
Copyright (C) 1985, 1990 Regents of the University of California.
Permission to use, copy, modify, and distribute this
software and its documentation for any purpose and without
fee is hereby granted, provided that the above copyright
notice appear in all copies. The University of California
makes no representations about the suitability of this
software for any purpose. It is provided "as is" without
express or implied warranty. Export of this software outside
of the United States of America may require an export license.

144
Makefile
View File

@ -4,33 +4,31 @@
MAGICDIR = .
PROGRAMS = magic
TECHS = scmos
TECH = scmos
LIBRARIES = database utils extflat
MODULES = bplane cmwind commands database dbwind debug drc extflat \
extract graphics netmenu plow resis select sim textio tiles \
utils windows wiring
# This was `cat VERSION`
VERSION := $(shell cat ${MAGICDIR}/VERSION)
MODULES = cmwind commands database dbwind debug drc extflat extract \
graphics netmenu plow resis select sim textio tiles utils \
windows wiring
MAKEFLAGS =
INSTALL_CAD_DIRS = windows doc ${TECHS}
INSTALL_CAD_DIRS = windows doc ${TECH}
-include defs.mak
include defs.mak
all: $(ALL_TARGET) techs
all: $(ALL_TARGET)
standard: mains
standard:
@echo --- errors and warnings logged in file make.log
@${MAKE} mains 2>&1 | tee -a make.log | egrep -i "(.c:|Stop.|---)"
tcl: tcllibrary
tcl:
@echo --- errors and warnings logged in file make.log
@${MAKE} tcllibrary 2>&1 | tee -a make.log | egrep -i "(.c:|Stop.|---)"
force:
@${MAKE} clean
@${MAKE} all
force: clean all
defs.mak:
@echo No \"defs.mak\" file found. Run "configure" to make one.
@exit 1
config:
${MAGICDIR}/configure
@ -38,70 +36,38 @@ config:
tcllibrary: database/database.h modules
@echo --- making Tcl shared libraries
for dir in ${PROGRAMS}; do \
(cd $$dir && ${MAKE} tcl-main) || exit 1; done
(cd $$dir && ${MAKE} tcl-main); done
mains: database/database.h modules libs
@echo --- making main programs
for dir in ${PROGRAMS}; do \
(cd $$dir && ${MAKE} main) || exit 1; done
(cd $$dir && ${MAKE} main); done
database/database.h: ${MAGICDIR}/database/database.h.in
database/database.h: database/database.h.in
@echo --- making header file database/database.h
${SCRIPTS}/makedbh ${MAGICDIR}/database/database.h.in database/database.h
${SCRIPTS}/makedbh database/database.h.in database/database.h
# tiles xyz => tiles/libtiles.o xyz/libxyz.o
MODULES_SUBDIR := $(shell for i in ${MODULES}; do echo "$${i}/lib$${i}.o"; done)
# tiles xyz => tiles/libtiles.a xyz/libxyz.a
LIBS_SUBDIR := $(shell for i in ${MODULES}; do echo "$${i}/lib$${i}.a"; done)
modules:
@echo --- making modules
for dir in ${MODULES} ${PROGRAMS}; do \
(cd $$dir && ${MAKE} module); done
.PHONY: FORCE
${MODULES_SUBDIR}: FORCE
@${MAKE} -C $(dir $@) module
libs:
@echo --- making libraries
for dir in ${LIBRARIES}; do \
(cd $$dir && ${MAKE} lib); done
.PHONY: modules
modules: database/database.h depend ${MODULES_SUBDIR}
${LIBS_SUBDIR}: FORCE
@${MAKE} -C $(dir $@) lib
# Force the tiles/utils modules to exist first for libdatabase.a
.PHONY: libs
libs: database/database.h depend tiles/libtiles.o utils/libutils.o ${LIBS_SUBDIR}
#
# extcheck - utility tool
# net2ir - utility tool
# oa - disabled (needs 'clean' target renaming)
SUBDIRS = bplane cmwind commands database dbwind debug drc extflat extract graphics \
magic netmenu plow resis select sim textio tiles utils windows wiring
BUNDLED_MODULES = readline lisp
# Unique list of all subdir that might have Depend file, we have to deduplicate otherwise
# MAKE will warning loudly. This list is somewhat empty when defs.mak does not exist
SUBDIRS_FILTERED := $(shell echo ${MODULES} ${PROGRAMS} ${SUBDIRS} | tr ' ' '\n' | sort | uniq)
SUBDIRS_DEPEND = $(addsuffix /Depend, ${SUBDIRS_FILTERED})
${SUBDIRS_DEPEND}: database/database.h
@echo --- making dependencies
${MAKE} -C $(dir $@) depend
.PHONY: depend
depend: defs.mak ${SUBDIRS_DEPEND}
.PHONY: techs
techs: depend
@echo --- making techs
for dir in ${TECHS}; do \
(cd $$dir && ${MAKE} all) || exit 1; done
depend: database/database.h
${RM} */Depend
for dir in ${MODULES} ${UNUSED_MODULES} ${PROGRAMS}; do \
(cd $$dir && ${MAKE} depend); done
install: $(INSTALL_TARGET)
install-magic:
@echo --- installing executable to $(DESTDIR)${INSTALL_BINDIR}
@echo --- installing runtime files to $(DESTDIR)${INSTALL_LIBDIR}
@${MAKE} install-real
@echo --- installing executable to $(DESTDIR)${BINDIR}
@echo --- installing runtime files to $(DESTDIR)${LIBDIR}
@${MAKE} install-real 2>&1 >> install.log
install-real: install-dirs
for dir in ${INSTALL_CAD_DIRS}; do \
@ -110,26 +76,24 @@ install-real: install-dirs
(cd $$dir && ${MAKE} install); done
install-tcl-dirs:
${MAGICDIR}/scripts/mkdirs $(DESTDIR)${INSTALL_BINDIR} \
$(DESTDIR)${INSTALL_MANDIR} $(DESTDIR)${INSTALL_SYSDIR} \
$(DESTDIR)${INSTALL_TCLDIR} $(DESTDIR)${INSTALL_TCLDIR}/bitmaps
${MAGICDIR}/scripts/mkdirs $(DESTDIR)${BINDIR} $(DESTDIR)${MANDIR} \
$(DESTDIR)${SYSDIR} $(DESTDIR)${TCLDIR} $(DESTDIR)${TCLDIR}/bitmaps
install-dirs:
${MAGICDIR}/scripts/mkdirs $(DESTDIR)${INSTALL_BINDIR} \
$(DESTDIR)${INSTALL_MANDIR} $(DESTDIR)${INSTALL_SYSDIR} \
$(DESTDIR)${INSTALL_SCMDIR}
${MAGICDIR}/scripts/mkdirs $(DESTDIR)${BINDIR} $(DESTDIR)${MANDIR} \
$(DESTDIR)${SYSDIR} $(DESTDIR)${SCMDIR}
install-tcl:
@echo --- installing executable to $(DESTDIR)${INSTALL_BINDIR}
@echo --- installing runtime files to $(DESTDIR)${INSTALL_LIBDIR}
@${MAKE} install-tcl-real
@echo --- installing executable to $(DESTDIR)${BINDIR}
@echo --- installing runtime files to $(DESTDIR)${LIBDIR}
@${MAKE} install-tcl-real 2>&1 >> install.log
install-tcl-real: install-tcl-dirs
for dir in ${INSTALL_CAD_DIRS} ${PROGRAMS}; do \
(cd $$dir && ${MAKE} install-tcl); done
clean:
for dir in ${SUBDIRS_FILTERED} ${TECHS} ${BUNDLED_MODULES}; do \
for dir in ${MODULES} ${PROGRAMS} ${TECH} ${UNUSED_MODULES}; do \
(cd $$dir && ${MAKE} clean); done
${RM} *.tmp */*.tmp *.sav */*.sav *.log TAGS tags
@ -139,19 +103,18 @@ distclean:
${RM} defs.mak old.defs.mak ${MAGICDIR}/scripts/defs.mak
${RM} ${MAGICDIR}/scripts/default.conf
${RM} ${MAGICDIR}/scripts/config.log ${MAGICDIR}/scripts/config.status
${RM} database/database.h
${RM} scripts/magic.spec magic-${VERSION} magic-${VERSION}.tgz
${RM} scripts/magic.spec magic-`cat VERSION` magic-`cat VERSION`.tgz
${RM} *.log
dist:
${RM} scripts/magic.spec magic-${VERSION} magic-${VERSION}.tgz
${SED} -e /@VERSION@/s%@VERSION@%${VERSION}% \
${RM} scripts/magic.spec magic-`cat VERSION` magic-`cat VERSION`.tgz
sed -e /@VERSION@/s%@VERSION@%`cat VERSION`% \
scripts/magic.spec.in > scripts/magic.spec
${LN} -nsf . magic-${VERSION}
tar zchvf magic-${VERSION}.tgz --exclude CVS \
--exclude magic-${VERSION}/magic-${VERSION} \
--exclude magic-${VERSION}/magic-${VERSION}.tgz \
magic-${VERSION}
ln -nsf . magic-`cat VERSION`
tar zchvf magic-`cat VERSION`.tgz --exclude CVS \
--exclude magic-`cat VERSION`/magic-`cat VERSION` \
--exclude magic-`cat VERSION`/magic-`cat VERSION`.tgz \
magic-`cat VERSION`
clean-mains:
for dir in ${PROGRAMS}; do \
@ -161,13 +124,6 @@ tags:
${RM} tags
find . ${MODULES} ${PROGRAMS} -name "*.[ch]" -maxdepth 1 | xargs ctags -o tags
TAGS:
TAGS:
${RM} TAGS
find . ${MODULES} ${PROGRAMS} -name "*.[ch]" -maxdepth 1 | xargs etags -o TAGS
setup-git:
git config --local include.path ../.gitconfig
git stash save
${RM} .git/index
git checkout HEAD -- "$$(git rev-parse --show-toplevel)"
git stash pop

View File

@ -1,57 +1,25 @@
![Continuous Integration](https://github.com/RTimothyEdwards/magic/actions/workflows/main.yml/badge.svg)
# MAGIC
1. General Information:
---------------------------------
Use your World Wide Web browser to read:
http://opencircuitdesign.com/magic/
http://vlsi.csl.cornell.edu/magic/
http://www.research.digital.com/wrl/magic/magic.html
Primary documentation is on the opencircuitdesign.com website under
various links, including "Download", "Compile", and "Install" for
information on obtaining, compiling, and installing the tool from
source; "Code History" for detailed comments on all code changes;
"Using Magic" for basic usage information including a complete on-line
command reference; "Technology Files" for essential documentation on how
to understand, edit, or write technology files for Magic; "Documentation"
for miscellaneous papers and historical documentation converted to HTML
format.
The current distribution version of magic is maintained by Tim Edwards
<tim@opencircuitdesign.com>. Please let me know of any problems/bugs
you find through the github Issues tracker.
Additional information from developer Rajit Manohar:
https://csl.yale.edu/~rajit/magic/
Of mainly historical interest only, now (available through the WayBack machine):
https://web.archive.org/web/20051217204815/http://www.research.compaq.com:80/wrl/projects/magic/magic.html
the "Documentation" link.
The current development versions of magic are maintained by Tim Edwards
<tim@opencircuitdesign.com> and the current distribution version is
maintained by Rajit Manohar <rajit@csl.cornell.edu>. Please let us
know of any problems/bugs you find. Development of versions 7.2 and
newer is generously funded by MultiGiG, Inc.
2. Compilation and Installation:
---------------------------------
See the file "INSTALL" in this directory, or "INSTALL_MacOS.md" for MacOS.
See the file "INSTALL" in this directory.
3. Version 8.3 Release Notes:
---------------------------------
During the course of version 8.2, magic moved to a git-oriented
development. There are no longer "stable" and "distribution"
versions. There is only the git repo with various development
branches.
First release contains the "bplane" implementation for the cell
plane pulled from the open source code for micromagic. This is
much more efficient than using the corner-stitched tile plane
for cells, and speeds up a number of methods, such as extraction,
by a factor of 3 to 5 or so, depending on the amount of hierarchy
in the design.
4. Version 8.2 Release Notes:
3. Version 8.2 Release Notes:
---------------------------------
As of the release of version 8.2, Version 8.1 is now the new stable
@ -72,15 +40,7 @@
magic extensions since version 7, including non-manhattan geometry,
stacked contacts, and DRC rule extensions.
Extended the extraction method to allow multiple extracted device
types per magic layer, depending on the surrounding context
(connecting layers, substrate, identifier layers, etc.).
Corrected the "extresist" method for non-FET devices, although it
continues to need fundamental work to remove its dependence on the
".sim" format files.
5. Version 8.1 Release Notes:
4. Version 8.1 Release Notes:
---------------------------------
As of the release of version 8.1, Version 8.0 is now the new stable
@ -94,7 +54,7 @@
name without any understanding of a substrate node and
connectivity.
6. Version 8.0 Release Notes:
5. Version 8.0 Release Notes:
---------------------------------
As of the release of version 8.0, Version 7.5 is now the new stable
@ -122,7 +82,7 @@
7) New extraction method "msubcircuit" with methods for specifying
parameter names for source/drain area and perimeter.
7. Version 7.5 Release Notes:
6. Version 7.5 Release Notes:
---------------------------------
Version 7.5 is the development branch. Version 7.5.0 is the same as
@ -177,7 +137,7 @@
See the online release notes for a more thorough list of features.
8. Version 7.4 Release Notes:
7. Version 7.4 Release Notes:
---------------------------------
Version 7.4 is the new stable distribution version of magic.
@ -189,7 +149,7 @@
not be a "What's new in 7.4" section, as there is not supposed
to be anything new in version 7.4.
9. Version 7.3 Release Notes:
8. Version 7.3 Release Notes:
---------------------------------
Magic release 7.3 incorporates a stacked contact model which is,
@ -237,7 +197,7 @@
28) New method for crash backups, including restore with "magic -r"
29) A number of other technology file additions and enhancements
10. Version 7.2 Release Notes:
9. Version 7.2 Release Notes:
---------------------------------
Magic release 7.2 incorporates the capability to run magic from the Tcl
@ -295,7 +255,7 @@
26) Improved techfile format with asterisk-notation and DRC
"surround", "overhang", and "rect_only" statements.
11. Version 7.1 Release Notes:
10. Version 7.1 Release Notes:
---------------------------------
Magic release 7.1 consolidates all known patches/features
@ -323,7 +283,7 @@
- tons of other small things that hopefully make the build process
nicer.
12. Releases prior to version 7:
11. Releases prior to version 7:
---------------------------------
What's new in 6.5.2:

36
TODO
View File

@ -1,32 +1,8 @@
I. Bugs to fix
I. Bugs to fix (also in magic-7.5 [stable]):
1. The "extresist" code needs to extract substrate networks. Moreover,
the "extresist" code really needs to have the dependence on
ext2sim removed, and instead read directly from .ext files. The
.sim format has no substrate connections, so this cannot be properly
represented. Also, there is nothing that is read from the .sim file
that is not already present in the .ext file.
1. The "extresist" code only recognizes original "fet" types, not
the new "device" types in the extract file.
2. "plow" should derive its rules from the DRC decks (using the new
routines that are meant for just that sort of thing).
3. It is possible to trick the net selection into an infinite loop in
unusual geometry situations. That these situations would be DRC
errors does not excuse the infinite loop behavior. The geometry
required is unusual enough that this is not a high priority item.
4. The LEF read/write should operate from the GDS rules and layers, not
the magic database layers. LEF setup should be put in the cifinput
and cifoutput sections in the techfile, not in its own section.
5. Implement a CRC checksum to replace (or complement) timestamps.
Cells are marked as invalid only if the checksum fails to match, not
if the timestamp is outdated. This helps with two problems: (1)
PDKs which are reinstalled but not changed, and (2) libraries which
are copied from one place to another but not changed.
6. Implement tile planes that can be defined as either maximum horizontal
stripes (default) or maximum vertical stripes. The latter, if applied
to vertically oriented route layers, vastly speeds up searches on
those layers. The code for manipulating tile planes with maximum
vertical stripes exists but is used only in by the maze router.
2. "plow" has been broken for some time. It should derive its rules
from the DRC decks (using the new routines that are meant for just
that sort of thing).

View File

@ -1 +1 @@
8.3.590
8.2.77

4
appimage/.gitignore vendored
View File

@ -1,4 +0,0 @@
*.tar.gz
prefix/
*.AppImage
appimagetool

View File

@ -1,59 +0,0 @@
FROM almalinux:10
USER root
# Build Dependencies (and dump version to logging)
RUN dnf install -y python3 zlib-devel ncurses-devel readline-devel cairo-devel freeglut-devel \
mesa-libGLU-devel mesa-libGL-devel libX11-devel libstdc++-devel gcc gcc-c++ make git tcsh \
zip \
&& echo "### rpm -qa:" \
&& rpm -qa | sort \
&& echo ""
#RUN dnf group install -y "Development Tools"
# Tcl/Tk
WORKDIR /tcl
RUN curl -L https://prdownloads.sourceforge.net/tcl/tcl9.0.1-src.tar.gz | tar --strip-components=1 -xzC . \
&& cd unix \
&& ./configure --prefix=/prefix \
&& make \
&& make install install-libraries install-msgs install-tzdata
WORKDIR /tk
RUN curl -L https://prdownloads.sourceforge.net/tcl/tk9.0.1-src.tar.gz | tar --strip-components=1 -xzC . \
&& cd unix \
&& ./configure --prefix=/prefix --with-tcl=/prefix/lib \
&& make \
&& make install install-libraries
WORKDIR /prefix/bin
RUN cp ./wish9.0 ./wish
RUN cp ./tclsh9.0 ./tclsh
# Magic
WORKDIR /magic
COPY . .
RUN ./configure \
--prefix=/prefix \
--with-tcl=/prefix/lib \
--with-tk=/prefix/lib \
&& make clean \
&& make database/database.h \
&& make -j$(nproc) \
&& make install
# Produce summary of what was created and confirm their DSOs
RUN echo "### filesystem:" \
find /prefix -printf "%y/%M/%m %i/%n %l %u/%U %g/%G %s/%b %T+/%T@\t%p\n"; \
ls -lR /prefix; \
find /prefix -type f -perm /111 -exec bash -c "echo \#\#\# {}; ldd -v {}" \; 2>/dev/null; \
for name in libgcc_s libstdc++ libpng liblzma libxml2 libz libcairo libGL libGLU; do \
find /lib64 /usr/lib64 -maxdepth 2 -name "*.so" -name "${name}*" -exec bash -c "echo \#\#\# {}; ldd -v {}" \; 2>/dev/null; \
done; \
echo "###"
WORKDIR /
RUN tar -czf /prefix.tar.gz -C ./prefix .
CMD ["/bin/bash"]

View File

@ -1,46 +0,0 @@
MAGIC_SRC_ROOT = ../..
RESOURCES := $(shell find ../rsc/ -type f)
ARCH := $(shell uname -m)
APPIMAGE = Magic-$(ARCH).AppImage
VERSION_MAGIC := $(shell cat $(MAGIC_SRC_ROOT)/VERSION)
VERSION_TSTAMP := $(shell git show -s "--format=%cs" | tr -d '-')
VERSION_HASH := $(shell git show -s "--format=%h")
VERSION_NUM ?= $(VERSION_MAGIC)~$(VERSION_TSTAMP)~$(VERSION_HASH)
VERSION := $(VERSION_NUM)
# Allow CI to override
APPIMAGETOOL_DOWNLOAD_URL ?= https://github.com/AppImage/appimagetool/releases/download/continuous/appimagetool-x86_64.AppImage
all: $(APPIMAGE)
.PHONY: prefix/bin/magic
prefix/bin/magic: Dockerfile Makefile
@echo "APPIMAGE=$(APPIMAGE)"
@echo "VERSION=$(VERSION)"
@echo "ARCH=$(ARCH)"
@echo "RESOURCES=$(RESOURCES)"
rm -rf prefix
docker build -t magic_build -f ./Dockerfile $(MAGIC_SRC_ROOT)
id=$$(docker create magic_build) ; \
docker cp $$id:/prefix ./prefix ; \
docker rm -v $$id
mkdir -p prefix/lib/tcl9.0.1
cp -r prefix/lib/tcl9.0 prefix/lib/tcl9.0.1/library
appimagetool:
curl -L "$(APPIMAGETOOL_DOWNLOAD_URL)" > ./appimagetool
chmod +x ./appimagetool
$(APPIMAGE): prefix/bin/magic appimagetool $(RESOURCES)
cp $(RESOURCES) ./prefix/
./appimagetool prefix
PREFIX ?= /usr/local
install:
install $(APPIMAGE) $(PREFIX)/bin/magic
.PHONY: clean
clean:
rm -f *.AppImage
rm -f prefix.tar.gz
rm -rf prefix

View File

@ -1,127 +0,0 @@
This is an AppImage that runs on all GNU/Linux platforms with:
* FUSE
* This excludes non-privileged Docker containers unfortunately, unless pre-extracted.
* GLIBC 2.38+
* Cairo 1.18+
* May require runtime CPU matching Linux ABI x86-64-v3 and newer (CPUs with SSE4.2/AVX2/BMI2/FMA via `lscpu`).
This AppImage build is based on EL10 (via AlmaLinux 10).
AlmaLinux 10 was first released on 27 May 2025.
# Version Info
See the AppImage main binary file naming, release tag information and AppInfo metadata
for the exact magic version inside the archive. When starting AppImage by default the
Tcl console banner can also provide version information, also using the `version` Tcl
command.
# Build Info
* Based on AlmaLinux 10 (EL10)
* Tcl/Tk 9.0.1
* and Magic 8.x
* all default modules enabled (including all Display drivers cairo/X11/OpenGL)
# FAQ: How to use
Download the *.AppImage file relevant to your platform and run:
```
chmod +x Magic-x86_64.AppImage
./Magic-x86_64.AppImage
```
Example startup with command line options:
```
./Magic-x86_64.AppImage -d XR -T scmos
```
# FAQ: How to use (inside docker / podman)
```
chmod +x Magic-x86_64.AppImage
### Podman or Docker, use :Z when rootless with selinux enabled
podman run --rm --device /dev/fuse --privileged \
-v "$(pwd):/tmp/work:Z" -v "/tmp/.X11-unix/X0:/tmp/.X11-unix/X0:Z" \
-e DISPLAY -ti almalinux:10
### Inside Docker:
dnf update -y
dnf install -y fuse libX11 cairo libGL libGLU
cd /tmp/work
./Magic-x86_64.AppImage -d XR -T scmos
```
# Building Requirements
* A reasonably recent GNU/Linux host
* GNU make
* Docker 20+
* Git
* curl
The final build is then packaged into an AppImage using AppImageTool on the host machine.
# Build Instructions
`make`
# Installation Instructions
`make install`
# FAQ: Is my CPU supported ?
This is built with the standard x86_64 Linux ABI version for AlmaLinux 10.
Use the command `/lib64/ld-linux-x86-64.so.2 --help` to see which CPUs your
Linux distribtion supports (and your CPU) look for the word "supported".
# FAQ: The DSO versioning link dependencies?
The information here provides an outline of what versions to expect from EL10
of the major dependencies, to assist you in a compatibility check with your
Linux distribution of choice.
The actual versions in our public releases can differ slightly inline with
the EL10 support compatibility and ABI versioning policies for the support
lifecycle of the distribution.
The most important items are the Direct Dependencies and the availabilty
of a suitable graphics DSO as per your '-d' choice.
Direct Runtime Dependencies (from /prefix/**):
| DSO Filename | DSO Symbol Version | Related Packages |
| :--------------------- | :------------------ | :------------------- |
| libc.so.6 | GLIBC_2.38 | glibc-2.39-37 |
| libz.so.1 | ZLIB_1.2.2 | zlib-ng-2.2.3-1 |
| | | zlib-ng-compat-2.2.3-1 |
Optional/Modular Runtime Dependencies (depending on graphics mode):
| DSO Filename | DSO Symbol Version | Related Packages |
| :--------------------- | :------------------ | :------------------- |
| libcairo.so.2 | | |
| libcairo.so.2.11802.0 | | cairo-1.18.2-2 |
| libGL.so.1 | | libglvnd-glx-1:1.7.0-7 |
| | | mesa-libGL-24.2.8-2 |
| libGLU.so.1 | | mesa-libGLU-9.0.3-7 |
Transitive/Third-Party Runtime Dependencies (for information only):
| DSO Filename | DSO Symbol Version | Related Packages |
| :--------------------- | :------------------ | :------------------- |
| libstdc++.so.6 | CXXABI_1.3.9 | gcc-c++-14.2.1-7 |
| libstdc++.so.6 | GLIBCXX_3.4 | gcc-c++-14.2.1-7 |
| libgcc_s.so.1 | GCC_4.2.0 | libgcc_s-14-20250110 |
| libxml2.so.2 | LIBXML2_2.6.0 | libxml2-2.12.5-5 |
| libpng16.so.16 | PNG16_0 | libpng-2:1.6.40-8 |
| liblzma.so.5 | XZ_5.0 | xz-devel-1:5.6.2-4 |
| libz.so.1 | ZLIB_1.2.9 | zlib-ng-2.2.3-1 |
| | | zlib-ng-compat-2.2.3-1 |

View File

@ -1,68 +0,0 @@
FROM centos/python-38-centos7:20210726-fad62e9
USER root
# CentOS7 went EOL on June 30, 2024 this builds out of vault.centos.org
RUN ls -l /etc/yum.repos.d/ \
&& cp /etc/yum.repos.d/CentOS-Base.repo /tmp/CentOS-Base.repo.old \
&& sed -e 's/mirror.centos.org/vault.centos.org/g' -i /etc/yum.repos.d/*.repo \
&& sed -e 's/^#.*baseurl=http/baseurl=http/g' -i /etc/yum.repos.d/*.repo \
&& sed -e 's/^mirrorlist=http/#mirrorlist=http/g' -i /etc/yum.repos.d/*.repo \
&& diff -u /tmp/CentOS-Base.repo.old /etc/yum.repos.d/CentOS-Base.repo; \
yum clean all \
&& yum -y update \
&& rm -f /tmp/CentOS-Base.repo.old
# Build Dependencies (and dump version to logging)
RUN yum install -y cairo-devel freeglut-devel gcc make tcsh \
&& echo "### rpm -qa:" \
&& rpm -qa | sort \
&& echo ""
# Tcl/Tk
WORKDIR /tcl
RUN curl -L https://prdownloads.sourceforge.net/tcl/tcl8.6.16-src.tar.gz | tar --strip-components=1 -xzC . \
&& cd unix \
&& ./configure --prefix=/prefix \
&& make \
&& make install
WORKDIR /tk
RUN curl -L https://prdownloads.sourceforge.net/tcl/tk8.6.16-src.tar.gz | tar --strip-components=1 -xzC . \
&& cd unix \
&& ./configure --prefix=/prefix --with-tcl=/prefix/lib \
&& make \
&& make install
WORKDIR /prefix/bin
RUN cp ./wish8.6 ./wish
RUN cp ./tclsh8.6 ./tclsh
# Magic
WORKDIR /magic
COPY . .
RUN ./configure \
--prefix=/prefix \
--with-tcl=/prefix/lib \
--with-tk=/prefix/lib \
--without-opengl \
&& make clean \
&& make database/database.h \
&& make -j$(nproc) \
&& make install
# Produce summary of what was created and confirm their DSOs
RUN echo "### filesystem:" \
find /prefix -printf "%y/%M/%m %i/%n %l %u/%U %g/%G %s/%b %T+/%T@\t%p\n"; \
ls -lR /prefix; \
find /prefix -type f -perm /111 -exec bash -c "echo \#\#\# {}; ldd -v {}" \; 2>/dev/null; \
for name in libgcc_s libstdc++ libpng liblzma libxml2 libz libcairo libGL libGLU; do \
find /lib64 /usr/lib64 -maxdepth 2 -name "*.so" -name "${name}*" -exec bash -c "echo \#\#\# {}; ldd -v {}" \; 2>/dev/null; \
done; \
echo "###"
WORKDIR /
RUN tar -czf /prefix.tar.gz -C ./prefix .
CMD ["/bin/bash"]

View File

@ -1,46 +0,0 @@
MAGIC_SRC_ROOT = ../..
RESOURCES := $(shell find ../rsc/ -type f)
ARCH := $(shell uname -m)
APPIMAGE = Magic-$(ARCH).AppImage
VERSION_MAGIC := $(shell cat $(MAGIC_SRC_ROOT)/VERSION)
VERSION_TSTAMP := $(shell git show -s "--format=%cs" | tr -d '-')
VERSION_HASH := $(shell git show -s "--format=%h")
VERSION_NUM ?= $(VERSION_MAGIC)~$(VERSION_TSTAMP)~$(VERSION_HASH)
VERSION := $(VERSION_NUM)
# Allow CI to override
APPIMAGETOOL_DOWNLOAD_URL ?= https://github.com/AppImage/appimagetool/releases/download/continuous/appimagetool-x86_64.AppImage
all: $(APPIMAGE)
.PHONY: prefix/bin/magic
prefix/bin/magic: Dockerfile Makefile
@echo "APPIMAGE=$(APPIMAGE)"
@echo "VERSION=$(VERSION)"
@echo "ARCH=$(ARCH)"
@echo "RESOURCES=$(RESOURCES)"
rm -rf prefix
docker build -t magic_build -f ./Dockerfile $(MAGIC_SRC_ROOT)
id=$$(docker create magic_build) ; \
docker cp $$id:/prefix ./prefix ; \
docker rm -v $$id
mkdir -p prefix/lib/tcl8.6.16
cp -r prefix/lib/tcl8.6 prefix/lib/tcl8.6.16/library
appimagetool:
curl -L "$(APPIMAGETOOL_DOWNLOAD_URL)" > ./appimagetool
chmod +x ./appimagetool
$(APPIMAGE): prefix/bin/magic appimagetool $(RESOURCES)
cp $(RESOURCES) ./prefix/
./appimagetool prefix
PREFIX ?= /usr/local
install:
install $(APPIMAGE) $(PREFIX)/bin/magic
.PHONY: clean
clean:
rm -f *.AppImage
rm -f prefix.tar.gz
rm -rf prefix

View File

@ -1,137 +0,0 @@
This is an AppImage that runs on all GNU/Linux platforms with:
* FUSE
* This excludes non-privileged Docker containers unfortunately, unless pre-extracted.
* GLIBC 2.17+
* Cairo 1.15+
* Supports all Linux x86_64 CPUs
This AppImage build is based on EL7 (via CentOS 7)
CentOS 7 was first released on 07 July 2014 and went end-of-life on 30 June 2024.
# Version Info
See the AppImage main binary file naming, release tag information and AppInfo metadata
for the exact magic version inside the archive. When starting AppImage by default the
Tcl console banner can also provide version information, also using the `version` Tcl
command.
# Build Info
* Based on CentOS 7 (EL7)
* Tcl/Tk 8.6.16
* and Magic 8.x
* all default modules enabled, but without OpenGL (includes Display drivers cairo/X11)
# FAQ: How to use
Download the *.AppImage file relevant to your platform and run:
```
chmod +x Magic-x86_64.AppImage
./Magic-x86_64.AppImage
```
Example startup with command line options:
```
./Magic-x86_64.AppImage -d XR -T scmos
```
# FAQ: How to use (inside docker / podman)
```
chmod +x Magic-x86_64.AppImage
### Podman or Docker, use :Z when rootless with selinux enabled
podman run --rm --device /dev/fuse --privileged \
-v "$(pwd):/tmp/work:Z" -v "/tmp/.X11-unix/X0:/tmp/.X11-unix/X0:Z" \
-e DISPLAY -ti centos:7
### Inside Docker:
echo "FIXUP yum from vault and update" \
&& ls -l /etc/yum.repos.d/ \
&& cp /etc/yum.repos.d/CentOS-Base.repo /tmp/CentOS-Base.repo.old \
&& sed -e 's/mirror.centos.org/vault.centos.org/g' -i /etc/yum.repos.d/*.repo \
&& sed -e 's/^#.*baseurl=http/baseurl=http/g' -i /etc/yum.repos.d/*.repo \
&& sed -e 's/^mirrorlist=http/#mirrorlist=http/g' -i /etc/yum.repos.d/*.repo \
&& diff -u /tmp/CentOS-Base.repo.old /etc/yum.repos.d/CentOS-Base.repo; \
yum clean all \
&& yum -y update \
&& rm -f /tmp/CentOS-Base.repo.old
yum install -y fuse libX11 cairo
cd /tmp/work
./Magic-x86_64.AppImage -d XR -T scmos
```
# Building Requirements
* A reasonably recent GNU/Linux host
* GNU make
* Docker 20+
* Git
* curl
The final build is then packaged into an AppImage using AppImageTool on the host machine.
# Build Instructions
`make`
# Installation Instructions
`make install`
# FAQ: Is my CPU supported ?
Supports all x86_64 CPUs. The Linux ABI in use is the original x86-64 ABI (v1).
Use the command `/lib64/ld-linux-x86-64.so.2 --help` to see which CPUs your
Linux distribtion supports (and your CPU) look for the word "supported".
# FAQ: The DSO versioning link dependencies?
The information here provides an outline of what versions to expect from EL7
of the major dependencies, to assist you in a compatibility check with your
Linux distribution of choice.
The actual versions in our public releases can differ slightly inline with
the EL7 support compatibility and ABI versioning policies for the support
lifecycle of the distribution.
The most important items are the Direct Dependencies and the availabilty
of a suitable graphics DSO as per your '-d' choice.
Direct Runtime Dependencies (from /prefix/**):
| DSO Filename | DSO Symbol Version | Related Packages |
| :--------------------- | :------------------ | :------------------- |
| libc.so.6 | GLIBC_2.14 | glibc-2.17-326 |
| libz.so.1 | ZLIB_1.2.2 | zlib-1.2.7-21 |
Optional/Modular Runtime Dependencies (depending on graphics mode):
| DSO Filename | DSO Symbol Version | Related Packages |
| :--------------------- | :------------------ | :------------------- |
| libcairo.so.2 | | |
| libcairo.so.2.11512.0 | | cairo-1.15.12-4 |
| libGL.so.1 | | |
| libglvnd-glx-1:1.0.1-0 | | mesa-libGL-18.3.4-12 |
| libGLU.so.1 | | mesa-libGLU-9.0.0-4 |
Transitive/Third-Party Runtime Dependencies (for information only):
| DSO Filename | DSO Symbol Version | Related Packages |
| :--------------------- | :------------------ | :------------------- |
| libc.so.6 | GLIBC_2.35 | glibc-2.17-326 |
| libstdc++.so.6 | GLIBCXX_3.4 | gcc-4.8.5-44 |
| libstdc++.so.6 | CXXABI_1.3.9 | gcc-4.8.5-44 |
| libgcc_s.so.1 | | |
| libgcc_s-4.8.5-20150702.so.1 | GCC_4.2.0 | libgcc-4.8.5-44 |
| libxml2.so.2 | LIBXML2_2.6.0 | libxml2-2.9.1-6 |
| libpng15.so.15 | | |
| libpng15.so.15.13.0 | PNG16_0 | libpng-1:1.5.13-8 |
| liblzma.so.5 | XZ_5.0 | xz-libs-5.2.2-2 |
| libz.so.1 | ZLIB_1.2.9 | zlib-1.2.7-21 |

View File

@ -1,58 +0,0 @@
FROM almalinux:8
USER root
# Build Dependencies (and dump version to logging)
RUN dnf install -y python311 zlib-devel ncurses-devel readline-devel cairo-devel freeglut-devel \
mesa-libGLU-devel mesa-libGL-devel libX11-devel libstdc++-devel gcc gcc-c++ make git tcsh \
&& echo "### rpm -qa:" \
&& rpm -qa | sort \
&& echo ""
#RUN dnf group install -y "Development Tools"
# Tcl/Tk
WORKDIR /tcl
RUN curl -L https://prdownloads.sourceforge.net/tcl/tcl8.6.16-src.tar.gz | tar --strip-components=1 -xzC . \
&& cd unix \
&& ./configure --prefix=/prefix \
&& make \
&& make install
WORKDIR /tk
RUN curl -L https://prdownloads.sourceforge.net/tcl/tk8.6.16-src.tar.gz | tar --strip-components=1 -xzC . \
&& cd unix \
&& ./configure --prefix=/prefix --with-tcl=/prefix/lib \
&& make \
&& make install
WORKDIR /prefix/bin
RUN cp ./wish8.6 ./wish
RUN cp ./tclsh8.6 ./tclsh
# Magic
WORKDIR /magic
COPY . .
RUN ./configure \
--prefix=/prefix \
--with-tcl=/prefix/lib \
--with-tk=/prefix/lib \
&& make clean \
&& make database/database.h \
&& make -j$(nproc) \
&& make install
# Produce summary of what was created and confirm their DSOs
RUN echo "### filesystem:" \
find /prefix -printf "%y/%M/%m %i/%n %l %u/%U %g/%G %s/%b %T+/%T@\t%p\n"; \
ls -lR /prefix; \
find /prefix -type f -perm /111 -exec bash -c "echo \#\#\# {}; ldd -v {}" \; 2>/dev/null; \
for name in libgcc_s libstdc++ libpng liblzma libxml2 libz libcairo libGL libGLU; do \
find /lib64 /usr/lib64 -maxdepth 2 -name "*.so" -name "${name}*" -exec bash -c "echo \#\#\# {}; ldd -v {}" \; 2>/dev/null; \
done; \
echo "###"
WORKDIR /
RUN tar -czf /prefix.tar.gz -C ./prefix .
CMD ["/bin/bash"]

View File

@ -1,46 +0,0 @@
MAGIC_SRC_ROOT = ../..
RESOURCES := $(shell find ../rsc/ -type f)
ARCH := $(shell uname -m)
APPIMAGE = Magic-$(ARCH).AppImage
VERSION_MAGIC := $(shell cat $(MAGIC_SRC_ROOT)/VERSION)
VERSION_TSTAMP := $(shell git show -s "--format=%cs" | tr -d '-')
VERSION_HASH := $(shell git show -s "--format=%h")
VERSION_NUM ?= $(VERSION_MAGIC)~$(VERSION_TSTAMP)~$(VERSION_HASH)
VERSION := $(VERSION_NUM)
# Allow CI to override
APPIMAGETOOL_DOWNLOAD_URL ?= https://github.com/AppImage/appimagetool/releases/download/continuous/appimagetool-x86_64.AppImage
all: $(APPIMAGE)
.PHONY: prefix/bin/magic
prefix/bin/magic: Dockerfile Makefile
@echo "APPIMAGE=$(APPIMAGE)"
@echo "VERSION=$(VERSION)"
@echo "ARCH=$(ARCH)"
@echo "RESOURCES=$(RESOURCES)"
rm -rf prefix
docker build -t magic_build -f ./Dockerfile $(MAGIC_SRC_ROOT)
id=$$(docker create magic_build) ; \
docker cp $$id:/prefix ./prefix ; \
docker rm -v $$id
mkdir -p prefix/lib/tcl8.6.16
cp -r prefix/lib/tcl8.6 prefix/lib/tcl8.6.16/library
appimagetool:
curl -L "$(APPIMAGETOOL_DOWNLOAD_URL)" > ./appimagetool
chmod +x ./appimagetool
$(APPIMAGE): prefix/bin/magic appimagetool $(RESOURCES)
cp $(RESOURCES) ./prefix/
./appimagetool prefix
PREFIX ?= /usr/local
install:
install $(APPIMAGE) $(PREFIX)/bin/magic
.PHONY: clean
clean:
rm -f *.AppImage
rm -f prefix.tar.gz
rm -rf prefix

View File

@ -1,126 +0,0 @@
This is an AppImage that runs on all GNU/Linux platforms with:
* FUSE
* This excludes non-privileged Docker containers unfortunately, unless pre-extracted.
* GLIBC 2.28+
* Cairo 1.15+
* Supports all Linux x86_64 CPUs
This AppImage build is based on EL8 (via AlmaLinux 8)
AlmaLinux 8 was first released on 20 March 2021, active support ends 31 May 2024,
security support ends 31 May 2029 (please see AlmaLinux bulletins for
up-to-date information).
# Version Info
See the AppImage main binary file naming, release tag information and AppInfo metadata
for the exact magic version inside the archive. When starting AppImage by default the
Tcl console banner can also provide version information, also using the `version` Tcl
command.
* Based on AlmaLinux 8 (EL8)
* Tcl/Tk 8.6.16
* and Magic 8.x
* all default modules enabled (including all Display drivers cairo/X11/OpenGL)
# FAQ: How to use
Download the *.AppImage file relevant to your platform and run:
```
chmod +x Magic-x86_64.AppImage
./Magic-x86_64.AppImage
```
Example startup with command line options:
```
./Magic-x86_64.AppImage -d XR -T scmos
```
# FAQ: How to use (inside docker / podman)
```
chmod +x Magic-x86_64.AppImage
### Podman or Docker, use :Z when rootless with selinux enabled
podman run --rm --device /dev/fuse --privileged \
-v "$(pwd):/tmp/work:Z" -v "/tmp/.X11-unix/X0:/tmp/.X11-unix/X0:Z" \
-e DISPLAY -ti almalinux:8
### Inside Docker:
dnf update -y
dnf install -y fuse libX11 cairo libGL libGLU
cd /tmp/work
./Magic-x86_64.AppImage -d XR -T scmos
```
# Building Requirements
* A reasonably recent GNU/Linux host
* GNU make
* Docker
* Git
* curl
The final build is then packaged into an AppImage using AppImageTool on the host machine.
# Build Instructions
`make`
# Installation Instructions
`make install`
# FAQ: Is my CPU supported ?
Supports all x86_64 CPUs. The Linux ABI in use is the original x86-64 ABI (v1).
Use the command `/lib64/ld-linux-x86-64.so.2 --help` to see which CPUs your
Linux distribtion supports (and your CPU) look for the word "supported".
# FAQ: The DSO versioning link dependencies?
The information here provides an outline of what versions to expect from EL8
of the major dependencies, to assist you with a compatibility check with your
Linux distribution of choice.
The actual versions in our public releases can differ slightly inline with
the EL8 support compatibility and ABI versioning policies for the support
lifecycle of the distribution.
The most important items are the Direct Dependencies and the availabilty
of a suitable graphics DSO as per your '-d' choice.
Direct Runtime Dependencies (from /prefix/**):
| DSO Filename | DSO Symbol Version | Related Packages |
| :--------------------- | :------------------ | :------------------- |
| libc.so.6 | GLIBC_2.14 | glibc-2.28-251 |
| libz.so.1 | ZLIB_1.2.2 | zlib-1.2.11-25 |
Optional/Modular Runtime Dependencies (depending on graphics mode):
| DSO Filename | DSO Symbol Version | Related Packages |
| :--------------------- | :------------------ | :------------------- |
| libcairo.so.2 | | |
| libcairo.so.2.11512.0 | | cairo-1.15.12-6 |
| libGL.so.1 | | libglvnd-glx-1:1.3.4-2 |
| | | mesa-libGL-23.1.4-4 |
| libGLU.so.1 | | mesa-libGLU-9.0.0-15 |
Transitive/Third-Party Runtime Dependencies (for information only):
| DSO Filename | DSO Symbol Version | Related Packages |
| :--------------------- | :------------------ | :------------------- |
| libc.so.6 | GLIBC_2.35 | glibc-2.28-251 |
| libstdc++.so.6 | GLIBCXX_3.4 | gcc-c++-8.5.0 |
| libstdc++.so.6 | CXXABI_1.3.9 | gcc-c++-8.5.0 |
| libgcc_s.so.1 | GCC_4.2.0 | libgcc-8.5.0-26 |
| libxml2.so.2 | | libxml2-2.9.7-19 |
| libpng16.so.16 | PNG16_0 | libpng-2:1.6.34-5 |
| liblzma.so.5 | | xz-libs-5.2.4-4 |
| libz.so.1 | ZLIB_1.2.9 | zlib-1.2.11-25 |

View File

@ -1,59 +0,0 @@
FROM almalinux:9
USER root
# Build Dependencies (and dump version to logging)
RUN dnf install -y python311 zlib-devel ncurses-devel readline-devel cairo-devel freeglut-devel \
mesa-libGLU-devel mesa-libGL-devel libX11-devel libstdc++-devel gcc gcc-c++ make git tcsh \
zip \
&& echo "### rpm -qa:" \
&& rpm -qa | sort \
&& echo ""
#RUN dnf group install -y "Development Tools"
# Tcl/Tk
WORKDIR /tcl
RUN curl -L https://prdownloads.sourceforge.net/tcl/tcl9.0.1-src.tar.gz | tar --strip-components=1 -xzC . \
&& cd unix \
&& ./configure --prefix=/prefix \
&& make \
&& make install install-libraries install-msgs install-tzdata
WORKDIR /tk
RUN curl -L https://prdownloads.sourceforge.net/tcl/tk9.0.1-src.tar.gz | tar --strip-components=1 -xzC . \
&& cd unix \
&& ./configure --prefix=/prefix --with-tcl=/prefix/lib \
&& make \
&& make install install-libraries
WORKDIR /prefix/bin
RUN cp ./wish9.0 ./wish
RUN cp ./tclsh9.0 ./tclsh
# Magic
WORKDIR /magic
COPY . .
RUN ./configure \
--prefix=/prefix \
--with-tcl=/prefix/lib \
--with-tk=/prefix/lib \
&& make clean \
&& make database/database.h \
&& make -j$(nproc) \
&& make install
# Produce summary of what was created and confirm their DSOs
RUN echo "### filesystem:" \
find /prefix -printf "%y/%M/%m %i/%n %l %u/%U %g/%G %s/%b %T+/%T@\t%p\n"; \
ls -lR /prefix; \
find /prefix -type f -perm /111 -exec bash -c "echo \#\#\# {}; ldd -v {}" \; 2>/dev/null; \
for name in libgcc_s libstdc++ libpng liblzma libxml2 libz libcairo libGL libGLU; do \
find /lib64 /usr/lib64 -maxdepth 2 -name "*.so" -name "${name}*" -exec bash -c "echo \#\#\# {}; ldd -v {}" \; 2>/dev/null; \
done; \
echo "###"
WORKDIR /
RUN tar -czf /prefix.tar.gz -C ./prefix .
CMD ["/bin/bash"]

View File

@ -1,46 +0,0 @@
MAGIC_SRC_ROOT = ../..
RESOURCES := $(shell find ../rsc/ -type f)
ARCH := $(shell uname -m)
APPIMAGE = Magic-$(ARCH).AppImage
VERSION_MAGIC := $(shell cat $(MAGIC_SRC_ROOT)/VERSION)
VERSION_TSTAMP := $(shell git show -s "--format=%cs" | tr -d '-')
VERSION_HASH := $(shell git show -s "--format=%h")
VERSION_NUM ?= $(VERSION_MAGIC)~$(VERSION_TSTAMP)~$(VERSION_HASH)
VERSION := $(VERSION_NUM)
# Allow CI to override
APPIMAGETOOL_DOWNLOAD_URL ?= https://github.com/AppImage/appimagetool/releases/download/continuous/appimagetool-x86_64.AppImage
all: $(APPIMAGE)
.PHONY: prefix/bin/magic
prefix/bin/magic: Dockerfile Makefile
@echo "APPIMAGE=$(APPIMAGE)"
@echo "VERSION=$(VERSION)"
@echo "ARCH=$(ARCH)"
@echo "RESOURCES=$(RESOURCES)"
rm -rf prefix
docker build -t magic_build -f ./Dockerfile $(MAGIC_SRC_ROOT)
id=$$(docker create magic_build) ; \
docker cp $$id:/prefix ./prefix ; \
docker rm -v $$id
mkdir -p prefix/lib/tcl9.0.1
cp -r prefix/lib/tcl9.0 prefix/lib/tcl9.0.1/library
appimagetool:
curl -L "$(APPIMAGETOOL_DOWNLOAD_URL)" > ./appimagetool
chmod +x ./appimagetool
$(APPIMAGE): prefix/bin/magic appimagetool $(RESOURCES)
cp $(RESOURCES) ./prefix/
./appimagetool prefix
PREFIX ?= /usr/local
install:
install $(APPIMAGE) $(PREFIX)/bin/magic
.PHONY: clean
clean:
rm -f *.AppImage
rm -f prefix.tar.gz
rm -rf prefix

View File

@ -1,128 +0,0 @@
This is an AppImage that runs on all GNU/Linux platforms with:
* FUSE
* This excludes non-privileged Docker containers unfortunately, unless pre-extracted.
* GLIBC 2.34+
* Cairo 1.17+
* May require runtime CPU matching Linux ABI x86-64-v2 and newer (CPUs with SSE4.2/CX16 via `lscpu`).
This AppImage build is based on EL9 (via AlmaLinux 9)
AlmaLinux 9 was first released on 26 May 2022, full support ends 31 May 2027,
maintenance support ends 31 May 2032 (please see AlmaLinux bulletins for
up-to-date information).
# Version Info
See the AppImage main binary file naming, release tag information and AppInfo metadata
for the exact magic version inside the archive. When starting AppImage by default the
Tcl console banner can also provide version information, also using the `version` Tcl
command.
# Build Info
* Based on AlmaLinux 9 (EL9)
* Tcl/Tk 9.0.1
* and Magic 8.x
* all default modules enabled (including all Display drivers cairo/X11/OpenGL)
# FAQ: How to use
Download the *.AppImage file relevant to your platform and run:
```
chmod +x Magic-x86_64.AppImage
./Magic-x86_64.AppImage
```
Example startup with command line options:
```
./Magic-x86_64.AppImage -d XR -T scmos
```
# FAQ: How to use (inside docker / podman)
```
chmod +x Magic-x86_64.AppImage
### Podman or Docker, use :Z when rootless with selinux enabled
podman run --rm --device /dev/fuse --privileged \
-v "$(pwd):/tmp/work:Z" -v "/tmp/.X11-unix/X0:/tmp/.X11-unix/X0:Z" \
-e DISPLAY -ti almalinux:9
### Inside Docker:
dnf update -y
dnf install -y fuse libX11 cairo libGL libGLU
cd /tmp/work
./Magic-x86_64.AppImage -d XR -T scmos
```
# Building Requirements
* A reasonably recent GNU/Linux host
* GNU make
* Docker
* Git
* curl
The final build is then packaged into an AppImage using AppImageTool on the host machine.
# Build Instructions
`make`
# Installation Instructions
`make install`
# FAQ: Is my CPU supported ?
This is built with the standard x86_64 Linux ABI version for AlmaLinux 9.
Use the command `/lib64/ld-linux-x86-64.so.2 --help` to see which CPUs your
Linux distribtion supports (and your CPU) look for the word "supported".
# FAQ: The DSO versioning link dependencies?
The information here provides an outline of what versions to expect from EL9
of the major dependencies, to assist you in a compatibility check with your
Linux distribution of choice.
The actual versions in our public releases can differ slightly inline with
the EL9 support compatibility and ABI versioning policies for the support
lifecycle of the distribution.
The most important items are the Direct Dependencies and the availabilty
of a suitable graphics DSO as per your '-d' choice.
Direct Runtime Dependencies (from /prefix/**):
| DSO Filename | DSO Symbol Version | Related Packages |
| :--------------------- | :------------------ | :------------------- |
| libc.so.6 | GLIBC_2.34 | glibc-2.34-168 |
| libz.so.1 | ZLIB_1.2.2 | zlib-1.2.11-40 |
Optional/Modular Runtime Dependencies (depending on graphics mode):
| DSO Filename | DSO Symbol Version | Related Packages |
| :--------------------- | :------------------ | :------------------- |
| libcairo.so.2 | | |
| libcairo.so.2.11704.0 | | cairo-1.17.4-7 |
| libGL.so.1 | | libglvnd-glx-1:1.3.4 |
| | | mesa-libGL-24.2.8-2 |
| libGLU.so.1 | | mesa-libGLU-9.0.1 |
Transitive/Third-Party Runtime Dependencies (for information only):
| DSO Filename | DSO Symbol Version | Related Packages |
| :--------------------- | :------------------ | :------------------- |
| libc.so.6 | GLIBC_2.35 | glibc-2.34-168 |
| libstdc++.so.6 | CXXABI_1.3.9 | gcc-c++-11.5.0-5 |
| libstdc++.so.6 | GLIBCXX_3.4 | gcc-c++-11.5.0-5 |
| libgcc_s.so.1 | GCC_4.2.0 | libgcc-11.5.0-2 |
| libxml2.so.2 | LIBXML2_2.6.0 | libxml2-2.9.13-9 |
| libpng16.so.16 | PNG16_0 | ibpng-2:1.6.37-12 |
| liblzma.so.5 | XZ_5.0 | xz-libs-5.2.5-8 |
| libz.so.1 | ZLIB_1.2.9 | zlib-1.2.11-40 |

View File

@ -1,39 +0,0 @@
#!/usr/bin/env bash
export CURDIR=$(dirname $(readlink -f "${0}"))
export PATH="${CURDIR}/bin":$PATH
export LD_LIBRARY_PATH=${CURDIR}/lib:$LD_LIBRARY_PATH
export CAD_ROOT="${CURDIR}/lib"
export MAGIC_WISH="${CURDIR}/bin/wish"
function my_echo() {
if [ "$MAGIC_VERBOSE" != "0" ]
then
echo -- $@
fi
}
# Attempt to set by default a valid 'ulimit -n' based on TCL version this
# will automatically apply valid limit inside docker running processes.
if [ "X${MAGIC_ULIMIT_NOFILE:+set}" = "X" ] # not set to something
then
if $MAGIC_WISH "${CURDIR}/version_check.tcl" | grep -q "=8\." # only needed for tcl8
then
if [ $(ulimit -Sn) -gt 1024 ] # only reduce >1024 to 1024
then
MAGIC_ULIMIT_NOFILE=1024
my_echo "# ulimit -Sn reduced from $(ulimit -Sn) to $MAGIC_ULIMIT_NOFILE"
fi
fi
fi
if [ "X$MAGIC_ULIMIT_NOFILE" != "X" ] # non empty
then
# Inform user we did this and hint at how to customize
my_echo "ulimit -Sn $MAGIC_ULIMIT_NOFILE # use \$MAGIC_ULIMIT_NOFILE to customize"
ulimit -Sn $MAGIC_ULIMIT_NOFILE
fi
my_echo "# Starting Magic"
exec "${CURDIR}/bin/magic" "$@"

View File

@ -1,8 +0,0 @@
[Desktop Entry]
Type=Application
Name=Magic
Icon=magic
Exec=magic
Comment=Magic - A VLSI Layout System
Categories=Development;
Terminal=true

View File

@ -1,65 +0,0 @@
<?xml version="1.0" encoding="iso-8859-1"?>
<!-- Generator: Adobe Illustrator 18.0.0, SVG Export Plug-In . SVG Version: 6.00 Build 0) -->
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">
<svg version="1.1" id="Capa_1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px"
viewBox="0 0 464.731 464.731" style="enable-background:new 0 0 464.731 464.731;" xml:space="preserve">
<g id="XMLID_207_">
<path id="XMLID_212_" d="M463.056,441.971l-45.894-43.145l29.759-55.521c0.8-1.508,0.379-3.398-1.029-4.395
c-1.388-1.011-3.305-0.832-4.487,0.424l-43.146,45.895l-55.533-29.746c-1.515-0.803-3.399-0.377-4.395,1.027
c-1.017,1.392-0.815,3.309,0.438,4.488l45.911,43.162l-29.747,55.518c-0.816,1.525-0.378,3.401,1.01,4.412
c1.41,0.996,3.326,0.816,4.502-0.438l43.149-45.912l55.507,29.746c1.506,0.802,3.393,0.378,4.393-1.027
C464.506,445.072,464.308,443.136,463.056,441.971z"/>
<path id="XMLID_211_" d="M369.086,94.641l-20.273,37.826c-1.04,1.918-0.479,4.307,1.285,5.588c1.783,1.271,4.215,1.029,5.71-0.559
l29.417-31.269l37.78,20.26c1.921,1.024,4.323,0.484,5.589-1.285c1.271-1.783,1.048-4.215-0.555-5.709l-31.245-29.385
l20.274-37.814c1.028-1.918,0.466-4.307-1.297-5.59c-1.766-1.268-4.216-1.025-5.713,0.558l-29.381,31.257l-37.814-20.273
c-1.936-1.026-4.325-0.467-5.589,1.301c-1.273,1.766-1.042,4.214,0.544,5.711L369.086,94.641z"/>
<path id="XMLID_210_" d="M123.956,360.06l-44.659,6.239l-17.611-41.484c-0.906-2.113-3.217-3.232-5.423-2.631
c-2.226,0.623-3.626,2.78-3.313,5.051l6.239,44.639L17.69,389.489c-2.1,0.908-3.23,3.217-2.614,5.424
c0.609,2.219,2.767,3.629,5.032,3.31l44.657-6.241l17.611,41.5c0.896,2.118,3.218,3.236,5.425,2.629
c2.206-0.617,3.626-2.765,3.312-5.043l-6.238-44.658l41.5-17.617c2.099-0.904,3.234-3.217,2.612-5.423
C128.383,361.147,126.221,359.745,123.956,360.06z"/>
<path id="XMLID_209_" d="M4.908,45.161l34.646,9.537l-0.23,35.832c-0.012,2.01,1.449,3.704,3.447,3.99
c1.976,0.271,3.851-0.969,4.377-2.901l9.521-34.565l35.923,0.225c2.01,0.016,3.702-1.447,3.992-3.441
c0.271-1.982-0.97-3.853-2.905-4.383l-34.627-9.547l0.213-35.881c0.018-2.01-1.466-3.701-3.441-3.988
c-1.983-0.273-3.856,0.965-4.383,2.901l-9.533,34.608L5.996,37.324c-1.991,0-3.701,1.463-3.974,3.441
C1.751,42.747,2.992,44.633,4.908,45.161z"/>
<path id="XMLID_208_" d="M278.019,234.519l139.775-18.477c1.586-0.21,2.762-1.555,2.762-3.143c0-1.587-1.176-2.928-2.762-3.142
L278.019,191.28l20.476-57.755c0.857-2.446,0.235-5.183-1.603-7.009c-1.828-1.844-4.567-2.445-7.01-1.586l-57.697,20.484
L213.708,5.688c-0.194-1.588-1.554-2.764-3.14-2.764c-1.584,0-2.935,1.176-3.146,2.764l-18.457,139.744l-57.772-20.502
c-2.448-0.875-5.181-0.258-7.014,1.586c-1.84,1.826-2.46,4.563-1.586,7.009l20.489,57.772l-139.73,18.46
c-1.584,0.214-2.762,1.555-2.762,3.142c0,1.588,1.178,2.933,2.762,3.143l139.73,18.461l-20.489,57.742
c-0.874,2.447-0.254,5.182,1.586,7.01c1.833,1.842,4.565,2.462,7.014,1.582l57.772-20.467l18.457,139.743
c0.212,1.583,1.563,2.764,3.146,2.764c1.586,0,2.945-1.181,3.14-2.764l18.477-139.743l57.727,20.486
c2.441,0.876,5.181,0.256,7.009-1.589c1.845-1.825,2.461-4.562,1.584-7.007L278.019,234.519z"/>
</g>
<g>
</g>
<g>
</g>
<g>
</g>
<g>
</g>
<g>
</g>
<g>
</g>
<g>
</g>
<g>
</g>
<g>
</g>
<g>
</g>
<g>
</g>
<g>
</g>
<g>
</g>
<g>
</g>
<g>
</g>
</svg>

Before

Width:  |  Height:  |  Size: 3.3 KiB

View File

@ -1,4 +0,0 @@
# Usage: wish version_check.tcl
puts "tcl_version=$tcl_version"
puts "tk_version=$tk_version"
exit 0

View File

@ -1,10 +0,0 @@
#
# rcsid "$Header: /usr/cvsroot/magic-8.0/drc/Makefile,v 1.1.1.1 2008/02/03 20:43:50 tim Exp $"
#
MODULE = bplane
MAGICDIR = ..
SRCS = bpDump.c bpUtils.c bpBins.c bpEnum.c bpMain.c bpStat.c
include ${MAGICDIR}/defs.mak
include ${MAGICDIR}/rules.mak

View File

@ -1,38 +0,0 @@
TODO
----
NOTE: nested enums are broken do to dynamic binning.
Don't rebuild entire bplane when bbox grows.
unsubbing sometimes.
Some (remaining) bplane design issues:
groups?
idea: support small number of groups by having
separate bplane for each group. Do selection this
way. Logically layered on top of bplanes - but may
want to integrate.
DECISION: defer for now.
pack/unpack?
Seems incompatible with user alloc/dealloc.
Complicated.
DECISION: Forget it.
coarse/fine with cache.
can be added later. should fit in nicely.
no special support needed.
integrated find/add?
can add later.
don't worry about it now.
May want to add attributes, via external hash.

View File

@ -1,719 +0,0 @@
// ************************************************************************
//
// Copyright (c) 1995-2002 Juniper Networks, Inc. All rights reserved.
//
// Permission is hereby granted, without written agreement and without
// license or royalty fees, to use, copy, modify, and distribute this
// software and its documentation for any purpose, provided that the
// above copyright notice and the following three paragraphs appear in
// all copies of this software.
//
// IN NO EVENT SHALL JUNIPER NETWORKS, INC. BE LIABLE TO ANY PARTY FOR
// DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES
// ARISING OUT OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF
// JUNIPER NETWORKS, INC. HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH
// DAMAGE.
//
// JUNIPER NETWORKS, INC. SPECIFICALLY DISCLAIMS ANY WARRANTIES,
// INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, AND
// NON-INFRINGEMENT.
//
// THE SOFTWARE PROVIDED HEREUNDER IS ON AN "AS IS" BASIS, AND JUNIPER
// NETWORKS, INC. HAS NO OBLIGATION TO PROVIDE MAINTENANCE, SUPPORT,
// UPDATES, ENHANCEMENTS, OR MODIFICATIONS.
//
// ************************************************************************
/* bpBins.c
*
* Routines for creating and manipulating bin arrays.
*
*/
#include <stdio.h>
#include <math.h>
#include "utils/utils.h"
#include "utils/malloc.h"
#include "database/database.h"
#include "utils/geometry.h"
#include "bplane/bplaneInt.h"
/* debug */
#define BPD 0
/* Tcl linked Parameters */
int bpMinBAPop = 10; /* don't sub(bin) when count less than this */
double bpMinAvgBinPop = 1.0; /* try to keep average bin pop at or
* below this
*/
/*
* ----------------------------------------------------------------------------
*
* roundUp -- Round up a number to a grid.
*
* ----------------------------------------------------------------------------
*/
static __inline__ int roundUp(int i, int res)
{
int r = (i % res);
/* Subtract negative number */
if (r > 0) r = r - res;
return i - r;
}
/*
* ----------------------------------------------------------------------------
*
* bpBinArrayNew -- allocate new bin array.
*
* ----------------------------------------------------------------------------
*/
static BinArray *bpBinArrayNew(int dx, /* x diameter of bins */
int dy, /* y diameter of bins */
Rect *bbox) /* area covered */
{
BinArray *new;
Rect abbox;
int w, h, dimX, dimY, numBins;
int size;
/* compute array dimensions */
w = roundUp(GEO_WIDTH(bbox),dx);
h = roundUp(GEO_HEIGHT(bbox),dy);
dimX = w/dx;
dimY = h/dy;
numBins = dimX*dimY;
/* allocate array */
size = sizeof(BinArray) + numBins*(sizeof(void *));
new = (BinArray *)callocMagic(1, size);
/* initial */
new->ba_bbox = *bbox;
new->ba_dx = dx;
new->ba_dy = dy;
new->ba_dimX = dimX;
new->ba_numBins = numBins;
/* pull bbox back one from top-edge, right-edge, to simplify index
* computation in bpEnumPush
*/
new->ba_bbox.r_xtop --;
new->ba_bbox.r_ytop --;
return new;
}
/*
* ----------------------------------------------------------------------------
*
* bpBinAdd -- add element to bin array
*
* ----------------------------------------------------------------------------
*/
void bpBinAdd(BinArray *ba,
Element *e)
{
int i; /* bin index */
/* compute bin index */
if(GEO_WIDTH(&e->e_rect) >= ba->ba_dx ||
GEO_HEIGHT(&e->e_rect) >= ba->ba_dy)
{
/* oversized */
i = ba->ba_numBins;
}
else
{
/* x and y indices */
int xi = (e->e_rect.r_xbot - ba->ba_bbox.r_xbot) / ba->ba_dx;
int yi = (e->e_rect.r_ybot - ba->ba_bbox.r_ybot) / ba->ba_dy;
i = xi + yi*ba->ba_dimX ;
}
/* add element */
if(bpBinType(ba,i) == BT_ARRAY)
{
/* sub-binned */
bpBinAdd(bpSubArray(ba,i), e);
}
else
{
/* simple list */
Element *next = bpBinList(ba,i);
/* link with next */
e->e_link = next;
if(next) next->e_linkp = &e->e_link;
/* link to head */
ba->ba_bins[i] = e;
e->e_linkp = (Element **) &ba->ba_bins[i];
}
}
/*
* ----------------------------------------------------------------------------
*
* bpBinArrayUnbuild - remove elements from bin array and Free the array
*
* Returns: (singly linked) list of elements formerly in the array
*
* ----------------------------------------------------------------------------
*/
static Element *bpBinArrayUnbuild(BinArray *ba)
{
Element *elements = NULL;
int numBins = ba->ba_numBins;
int i;
/* empty the bins */
for(i=0;i<=numBins;i++)
{
Element *l;
if(bpBinType(ba,i) == BT_ARRAY)
{
/* sub-array, unbuild recursively */
l = bpBinArrayUnbuild(bpSubArray(ba,i));
}
else
{
/* Simple list */
l = bpBinList(ba,i);
}
/* collect elements */
while(l)
{
Element *e = l;
l = e->e_link;
e->e_link = elements;
elements = e;
}
}
/* free the array */
freeMagic((char *)ba);
return elements;
}
/*
* ----------------------------------------------------------------------------
* bpListExceedsQ --
*
* check if element list exceeds given length
*
* Returns size of list.
*
* ----------------------------------------------------------------------------
*/
static __inline__ int
bpListExceedsQ(Element *e, /* list */
int n) /* length to check against */
{
n++;
while(e && n)
{
n--;
e = e->e_link;
}
return n==0;
}
/*
* ----------------------------------------------------------------------------
*
* bpBinArraySizeIt -- choose bin sizes for new bin array.
*
* RESULT:
*
* normally returns TRUE,
* returns FALSE on failure: could not come up with binning that
* makes progress.
*
* NOTE: the various 'return' parameters are not set on failure.
*
* ----------------------------------------------------------------------------
*/
static __inline__ bool
bpBinArraySizeIt(Rect *bbox, /* bin array bbox */
Element *elements, /* initial elements */
int *dxp, /* return bin x-diameter here */
int *dyp, /* return bin y-diameter here */
int *maxDXp,
int *maxDYp,
int *numBinsp, /* return number of bins here */
int *countp) /* return number of elements here */
{
BinArray *ba;
int count;
double numBins; /* need double to avoid overflow on tentative calc. */
int h = GEO_HEIGHT(bbox);
int w = GEO_WIDTH(bbox);
int dx,dy; /* individual bin diameter */
int maxEX, maxEY; /* max element dimensions */
int maxDX, maxDY; /* max bin diameter allowed */
int xDim, yDim; /* array dimensions */
int maxBins; /* max number of bins
* (due to bpMinAvgBinPop)
*/
/* compute max element dimensions
* (would like bins coarser than max dimensisons)
*/
{
Element *e;
maxEX = 0;
maxEY = 0;
count = 0;
for(e=elements; e; e=e->e_link)
{
int ew = GEO_WIDTH(&e->e_rect);
int eh = GEO_HEIGHT(&e->e_rect);
maxEX = MAX(maxEX,ew);
maxEY = MAX(maxEY,eh);
count++;
}
}
/* if too few elements, don't bother with binning */
if(count < bpMinBAPop) return FALSE;
/* if too tiny don't subbin,
* avoid nasty corner-cases in code below
*/
if(h<2 || w<2) return FALSE;
/* tentatively choose bin size to fit all elements */
dx = maxEX+1;
dy = maxEY+1;
/* ensure we get at least two bins, so that
* subbining of sparse designs will work.
*/
maxDX = (w+1)/2;
maxDY = (h+1)/2;
/*
fprintf(stderr,"bpBinArraySizeIt, initial "
"maxEX=%d maxEY=%d maxDX=%d maxDY=%d dx=%d dy=%d\n",
maxEX,maxEY,maxDX,maxDY,dx,dy);
*/
if(dx <= maxDX)
{
/* x is cool */
if(dy <= maxDY)
{
/* totally cool */
;
}
else
{
/* y-dim too big for two bins, but x-dim cool,
* just reduce in x this time.
*/
dy = h+1;
}
}
else
{
/* x-dim too big for two bins */
if(dy <= maxDY)
{
/* x-dim too big for two bins but y=dim cool,
* just reduce in y this time
*/
dx = w+1;
}
else
{
/* BOTH x-dim and y-dim too big for two bins.
* We are screwed: will have some oversized.
*
* Choose betwen splitting in two horizontally or
* vertically, by which ever method results in the minimum
* number of oversized elements.
*/
int xOver=0; /* number of oversized if we reduce x-dim. */
int yOver=0; /* number of oversized if we reduce y-dim. */
Element *e;
/* count potential oversized */
for(e=elements; e; e=e->e_link)
{
int ew = GEO_WIDTH(&e->e_rect);
int eh = GEO_HEIGHT(&e->e_rect);
if(ew >= maxDX) xOver++;
if(eh >= maxDY) yOver++;
}
if(xOver<yOver)
{
/* reduce x-dim to minimize oversized */
dx = maxDX;
dy = h+1;
}
else
{
/* are we making progress? */
if(yOver == count) return FALSE;
/* reduce y-dim to minimize oversized */
dx = w+1;
dy = maxDY;
}
}
}
/* tentative number of bins */
xDim = roundUp(w,dx)/dx;
yDim = roundUp(h,dy)/dy;
numBins = xDim*((double)yDim);
/* if too many bins, need to increase at least one dimension */
/* (note this step will NOT reduce dimensions) */
maxBins = MAX(count / bpMinAvgBinPop,1);
/*
fprintf(stderr,"DEBUG numBins = %g count= %d bpMinAvgBinPop=%f maxBins= %d\n",
numBins,count,bpMinAvgBinPop,maxBins);
*/
if(numBins>maxBins)
{
if(dx == w+1)
{
/* can't increase x-dim, so try increasing y-dim */
int yDimTarget = maxBins/xDim;
dy = (h+1) / MAX(yDimTarget,1);
dy = MIN(dy,maxDY);
}
else if (dy == h+1)
{
/* can't increase y-dim, so try increasing x-dim */
int xDimTarget = maxBins/yDim;
dx = (w+1) / MAX(xDimTarget,1);
dx = MIN(dx,maxDX);
}
else
{
/* try for square bins */
double area = h * (w + 0.0);
int d = MAX(sqrt(area/maxBins),1);
if(d<dx)
{
/* target d too small in x-dim
* leave xdim fixed and just increase y-dim
*/
int yDimTarget = maxBins/xDim;
dy = (h+1) / MAX(yDimTarget,1);
dy = MIN(dy,maxDY);
}
else if (d<dy)
{
/* target d too small in y-dim
* leave xdim fixed and just increase y-dim
*/
int xDimTarget = maxBins/yDim;
dx = (w+1) / MAX(xDimTarget,1);
dx = MIN(dx,maxDX);
}
else if(d>maxDX)
{
/* d too big for x-dim
* (this can happen for tall skinny bins)
*
* make x-dim maximal, and adjust y accordingly
*/
dx = w+1;
dy = MAX((h+1)/maxBins,dy);
dy = MIN(dy,maxDY);
}
else if(d>maxDY)
{
/* d too big for y-dim
* (this can happen for long squat bins)
*
* make y-dim maximal, and adjust x-dim accordingly
*/
dy = h+1;
dx = MAX((w+1)/maxBins,dx);
dx = MIN(dx,maxDX);
}
else
{
/* we're cool, create square bins */
dx = d;
dy = d;
}
}
/* update numBins */
xDim = roundUp(w,dx)/dx;
yDim = roundUp(h,dy)/dy;
numBins = xDim*yDim;
}
/* DEBUG */
if(BPD)
{
fprintf(stderr,"\nDEBUG bpBinArraySizeIt DONE, count=%d h=%d w=%d\n"
"\tmaxDX=%d maxDY=%d maxBins=%d\n"
"\tnumBins=%g dx=%d dy=%d\n",
count,h,w,
maxDX,maxDY,maxBins,
numBins,dx,dy);
}
/* set results */
if(dxp) *dxp = dx;
if(dyp) *dyp = dy;
if(maxDXp) *maxDXp = maxDX;
if(maxDYp) *maxDYp = maxDY;
if(numBinsp) *numBinsp = numBins;
if(countp) *countp = count;
/* success */
return TRUE;
}
/*
* ----------------------------------------------------------------------------
*
* bpBinArrayBuild1 -- build and populate bin array of given area and
* bin size.
*
* Returns: pointer to new bin array.
*
* ----------------------------------------------------------------------------
*/
static BinArray *bpBinArrayBuild1(Rect *bbox,
Element *elements, /* initial elements */
int dx, /* bin diameter */
int dy)
{
BinArray *ba;
/* build bin array */
ba = bpBinArrayNew(dx, dy, bbox);
/* transfer elements to bin array */
while(elements)
{
Element *e;
/* pop list */
e = elements;
elements = e->e_link;
bpBinAdd(ba, e);
}
return ba;
}
/*
* ----------------------------------------------------------------------------
*
* bpBinArrayBuild -- build and populate bin array of given area,
*
* NOTE: optimal bin size determined by trial and error.
* oversized subbinned, as indicated.
*
* Returns: pointer to new bin array, NULL on failure.
*
* ----------------------------------------------------------------------------
*/
BinArray *bpBinArrayBuild(Rect bbox,
Element *elements, /* initial elements */
bool subbin) /* subbin as needed */
{
BinArray *ba;
int dx,dy; /* individual bin diameter */
int maxDX, maxDY;
int numBins;
int count;
/* Added by Tim, 2/19/2024 */
/* This line is not supposed to be needed? */
if ((!subbin) && ((pointertype)elements & BT_ARRAY)) return NULL;
if(BPD) DumpRect("#### bpBinArrayBuild, TOP bbox= ", &bbox);
/* figure out good bin dimensions */
if(!bpBinArraySizeIt(&bbox,
elements,
&dx,
&dy,
&maxDX,
&maxDY,
&numBins,
&count)) return NULL;
/* build the bin array */
ba = bpBinArrayBuild1(&bbox, elements, dx, dy);
if(!subbin) return ba;
/* sub-bin normal bins */
{
int dimX = ba->ba_dimX;
int i;
for(i=0;i<numBins;i++)
{
BinArray *sub;
sub = bpBinArrayBuild(bpBinArea(ba,i),
bpBinList(ba, i),
TRUE);
if(sub)
{
ba->ba_bins[i] =
(void *) ((pointertype) sub | BT_ARRAY);
}
}
}
/* sub-bin oversized */
{
BinArray *sub;
sub = bpBinArrayBuild(bbox,
bpBinList(ba, numBins),
TRUE);
if(sub)
{
ba->ba_bins[numBins] =
(void *) ((pointertype) sub | BT_ARRAY);
}
}
if(BPD)
{
DumpRect("\n#### bpBinArrayBuild, DONE bbox= ", &bbox);
fprintf(stderr,"\n");
}
return ba;
}
/*
* ----------------------------------------------------------------------------
*
* bpBinsUpdate -- update bplane bins
*
* Called prior to enumerations.
*
* ----------------------------------------------------------------------------
*/
int bpBinLife = 0;
void bpBinsUpdate(BPlane *bp)
{
Rect bbox;
bool oldBins;
/* rebuild whenever inbox gets big */
if(!bpListExceedsQ(bp->bp_inBox, bpMinBAPop-1)) return;
/* fprintf(stderr,"DEBUG bpBinsUpdate - rebuilding bins.\n"); */
/* do bins already exist ? */
oldBins = (bp->bp_rootNode != 0);
/* if bins exist, dissolve them */
if(oldBins)
{
Element *elist = bpBinArrayUnbuild(bp->bp_rootNode);
/* add inbox to list */
while(bp->bp_inBox)
{
/* pop from inbox */
Element *e = bp->bp_inBox;
bp->bp_inBox = e->e_link;
/* add to elist */
e->e_link = elist;
elist = e;
}
bp->bp_inBox = elist;
}
/* compute accurate bbox */
{
Element *e = bp->bp_inBox;
bbox = e->e_rect;
for(e=bp->bp_inBox; e; e=e->e_link)
{
GeoIncludeRectInBBox(&e->e_rect, &bbox);
}
}
/* if rebuild, double bounding box, to avoid too many rebuilds */
if(oldBins)
{
int dx = GEO_WIDTH(&bbox)/2;
int dy = GEO_HEIGHT(&bbox)/2;
bbox.r_xbot -= dx;
bbox.r_ybot -= dy;
bbox.r_xtop += dx;
bbox.r_ytop += dy;
}
/* build and populate bin array */
bp->bp_rootNode = bpBinArrayBuild(bbox, bp->bp_inBox, TRUE);
if(bp->bp_rootNode) bp->bp_inBox = NULL;
bp->bp_binArea = bbox;
bp->bp_binLife = bpBinLife;
bp->bp_inAdds = 0;
/* if(BPD) bpDump(bp, 0); */
}

View File

@ -1,328 +0,0 @@
// ************************************************************************
//
// Copyright (c) 1995-2002 Juniper Networks, Inc. All rights reserved.
//
// Permission is hereby granted, without written agreement and without
// license or royalty fees, to use, copy, modify, and distribute this
// software and its documentation for any purpose, provided that the
// above copyright notice and the following three paragraphs appear in
// all copies of this software.
//
// IN NO EVENT SHALL JUNIPER NETWORKS, INC. BE LIABLE TO ANY PARTY FOR
// DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES
// ARISING OUT OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF
// JUNIPER NETWORKS, INC. HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH
// DAMAGE.
//
// JUNIPER NETWORKS, INC. SPECIFICALLY DISCLAIMS ANY WARRANTIES,
// INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, AND
// NON-INFRINGEMENT.
//
// THE SOFTWARE PROVIDED HEREUNDER IS ON AN "AS IS" BASIS, AND JUNIPER
// NETWORKS, INC. HAS NO OBLIGATION TO PROVIDE MAINTENANCE, SUPPORT,
// UPDATES, ENHANCEMENTS, OR MODIFICATIONS.
//
// ************************************************************************
/* bpDump.c
*
* routines to dump bin system (for debugging)
*
*/
#include <stdio.h>
#include "utils/utils.h"
#include "database/database.h"
#include "utils/geometry.h"
#include "cif/cif.h"
#include "bplane/bplaneInt.h"
static int bpDumpFlags; /* set by bpDump, used by subroutines */
/*
* ----------------------------------------------------------------------------
* bpIndent --
*
* tab over n spaces on stderr
*
* ----------------------------------------------------------------------------
*/
static void bpIndent(int n)
{
int i;
for(i=0;i<n;i++) fprintf(stderr," ");
}
/*
* ----------------------------------------------------------------------------
* bpDumpRect --
*
* list rects.
*
* ----------------------------------------------------------------------------
*/
void bpDumpRect(Rect *r)
{
if(bpDumpFlags & BPD_INTERNAL_UNITS)
{
fprintf(stderr,"%d ",
r->r_xbot);
fprintf(stderr,"%d ",
r->r_ybot);
fprintf(stderr,"%d ",
r->r_xtop);
fprintf(stderr,"%d",
r->r_ytop);
}
#ifdef CIF_MODULE
else
{
float oscale;
oscale = CIFGetOutputScale(1000);
fprintf(stderr,"%f ",
oscale * (float)r->r_xbot);
fprintf(stderr,"%f ",
oscale * (float)r->r_ybot);
fprintf(stderr,"%f ",
oscale * (float)r->r_xtop);
fprintf(stderr,"%f",
oscale * (float)r->r_ytop);
}
#endif
}
/*
* ----------------------------------------------------------------------------
* bpDumpElements --
*
* list rects.
*
* ----------------------------------------------------------------------------
*/
void bpDumpElements(Element *list, int indent)
{
Element *e;
for(e = list; e; e=e->e_link)
{
bpIndent(indent);
fprintf(stderr,"{element ");
if(bpDumpFlags & BPD_LABELED)
{
LabeledElement *le = (LabeledElement *) e;
fprintf(stderr,"%s ", le->le_text);
}
bpDumpRect(&e->e_rect);
fprintf(stderr,"}\n");
}
}
/*
* ----------------------------------------------------------------------------
* bpDumpEnums --
*
* list active enumerations
*
* ----------------------------------------------------------------------------
*/
void bpDumpEnums(BPEnum *bpe, int indent)
{
for(; bpe; bpe=bpe->bpe_next)
{
bpIndent(indent);
fprintf(stderr,"{enum \"%s\"}",
bpe->bpe_id);
}
}
/*
* ----------------------------------------------------------------------------
* bpBinArrayDump --
*
* recursively dump hierarchical bin system
*
* ----------------------------------------------------------------------------
*/
static void bpBinArrayDump(BinArray *ba, int indent)
{
int numBins = ba->ba_numBins;
int dx = ba->ba_dx;
int dy = ba->ba_dy;
int dimX = ba->ba_dimX;
int dimY = numBins/dimX;
Rect *bbox = &ba->ba_bbox;
int xi,yi;
/* open */
bpIndent(indent);
fprintf(stderr,"{bin-array ");
if(bpDumpFlags & BPD_INTERNAL_UNITS)
{
fprintf(stderr,"{dx %d} {dy %d} ",
dx,dy);
}
#ifdef CIF_MODULE
else
{
float oscale;
oscale = CIFGetOutputScale(1000);
fprintf(stderr,"{dx %f} ",
(float)dx * oscale);
fprintf(stderr,"{dy %f} ",
(float)dy * oscale);
}
#endif
fprintf(stderr,"{dimX %d} {dimY %d} { bbox ",
dimX,
dimY);
bpDumpRect(bbox);
fprintf(stderr," }\n");
/* bins */
for(yi=0; yi<dimY; yi++)
{
for(xi=0; xi<dimX; xi++)
{
Rect area;
int i = xi + yi*dimX;
area.r_xbot = bbox->r_xbot + xi*dx;
area.r_ybot = bbox->r_ybot + yi*dy;
area.r_xtop = area.r_xbot + dx;
area.r_ytop = area.r_ybot + dy;
/* skip empty bins */
if(bpBinEmpty(ba,i)) continue;
/* open bin */
bpIndent(indent+2);
fprintf(stderr,"{bin {number %d} { bbox ",
i);
bpDumpRect(&area);
fprintf(stderr," }\n");
/* list bin contents */
if(bpBinType(ba,i) == BT_ARRAY)
{
/* dump sub array */
bpBinArrayDump( bpSubArray(ba,i),
indent+4);
}
else
{
/* list elements */
bpDumpElements(bpBinList(ba,i),indent+4);
}
/* close bin */
bpIndent(indent+2);
fprintf(stderr,"}\n");
}
}
/* oversized */
if(!bpBinEmpty(ba,numBins))
{
/* open oversized */
bpIndent(indent+2);
fprintf(stderr,"{oversized {bbox ");
bpDumpRect(bbox);
fprintf(stderr,"}\n");
/* list bin contents */
if(bpBinType(ba,numBins) == BT_ARRAY)
{
/* dump sub array */
bpBinArrayDump( bpSubArray(ba,numBins),
indent+4);
}
else
{
/* list elements */
bpDumpElements(bpBinList(ba,numBins),indent+4);
}
/* close oversized */
bpIndent(indent+2);
fprintf(stderr,"}\n");
}
/* close bin array */
bpIndent(indent);
fprintf(stderr,"}\n");
}
/*
* ----------------------------------------------------------------------------
* bpDump --
*
* dump bplane (for debugging)
*
* ----------------------------------------------------------------------------
*/
void bpDump(BPlane *bp, int flags)
{
fprintf(stderr, "======= BPLANE DUMP ======\n");
bpDumpFlags = flags;
/* open bplane */
fprintf(stderr,"{bplane {count %d} {bbox ",
bp->bp_count);
bpDumpRect(&bp->bp_bbox);
fprintf(stderr,"}\n");
/* list in box rects */
bpIndent(2);
fprintf(stderr,"{in_box\n");
bpDumpElements(bp->bp_inBox,4);
bpIndent(2);
fprintf(stderr,"}\n");
/*** bins ***/
bpIndent(2);
fprintf(stderr,"{binned {area ");
bpDumpRect(&bp->bp_binArea);
fprintf(stderr,"}\n");
if(bp->bp_rootNode) bpBinArrayDump(bp->bp_rootNode, 4);
bpIndent(2);
fprintf(stderr,"}\n");
/*** enums ***/
bpIndent(2);
fprintf(stderr,"{enums\n");
bpDumpEnums(bp->bp_enums,4);
bpIndent(2);
fprintf(stderr,"}\n");
/* close bplane */
fprintf(stderr,"}\n");
}

View File

@ -1,166 +0,0 @@
// ************************************************************************
//
// Copyright (c) 1995-2002 Juniper Networks, Inc. All rights reserved.
//
// Permission is hereby granted, without written agreement and without
// license or royalty fees, to use, copy, modify, and distribute this
// software and its documentation for any purpose, provided that the
// above copyright notice and the following three paragraphs appear in
// all copies of this software.
//
// IN NO EVENT SHALL JUNIPER NETWORKS, INC. BE LIABLE TO ANY PARTY FOR
// DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES
// ARISING OUT OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF
// JUNIPER NETWORKS, INC. HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH
// DAMAGE.
//
// JUNIPER NETWORKS, INC. SPECIFICALLY DISCLAIMS ANY WARRANTIES,
// INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, AND
// NON-INFRINGEMENT.
//
// THE SOFTWARE PROVIDED HEREUNDER IS ON AN "AS IS" BASIS, AND JUNIPER
// NETWORKS, INC. HAS NO OBLIGATION TO PROVIDE MAINTENANCE, SUPPORT,
// UPDATES, ENHANCEMENTS, OR MODIFICATIONS.
//
// ************************************************************************
/* bpEnum.c -
*
* Search routines for bplanes
*
*/
#include <stdio.h>
#include "utils/utils.h"
#include "database/database.h"
#include "utils/geometry.h"
#include "bplane/bplaneInt.h"
/*
* ----------------------------------------------------------------------------
* BPEnumInit --
*
* set up search.
*
* ----------------------------------------------------------------------------
*/
void BPEnumInit(BPEnum *bpe, /* enum to initialize */
BPlane *bp,
const Rect *area, /* search area */
int match,
const char *id) /* for debugging */
{
bool inside = FALSE;
bpe->bpe_plane = bp;
bpe->bpe_id = id;
bpe->bpe_match = match;
bpe->bpe_top = bpe->bpe_stack;
/*
fprintf(stderr,"DEBUG bpEnumInit, match=%d id=%s\n",
match, id);
*/
/* link enum to bplane */
bpe->bpe_next = bp->bp_enums;
bp->bp_enums = bpe;
switch (match)
{
case BPE_EQUAL:
GeoCanonicalRect(area, &bpe->bpe_srchArea);
bpe->bpe_nextElement = IHashLookUp(bp->bp_hashTable, &bpe->bpe_srchArea);
bpe->bpe_top->bps_state = BPS_HASH;
/* don't need to setup stack, just return */
return;
case BPE_ALL:
/* If we start 'INSIDE', no match checks will be done */
bpe->bpe_top->bps_state = BPS_BINS_INSIDE;
inside = TRUE;
break;
case BPE_TOUCH:
GeoCanonicalRect(area, &bpe->bpe_srchArea);
inside = GEO_SURROUND(&bpe->bpe_srchArea, &bp->bp_bbox);
if(inside)
{
bpe->bpe_top->bps_state = BPS_BINS_INSIDE;
}
else
{
bpe->bpe_top->bps_state = BPS_BINS;
bpe->bpe_subBinMinX = GEO_WIDTH(&bpe->bpe_srchArea)/2;
bpe->bpe_subBinMinY = GEO_HEIGHT(&bpe->bpe_srchArea)/2;
bpBinsUpdate(bp);
}
break;
case BPE_OVERLAP:
GeoCanonicalRect(area, &bpe->bpe_srchArea);
GEO_EXPAND(&bpe->bpe_srchArea, -1, &bpe->bpe_srchArea);
inside = GEO_SURROUND(&bpe->bpe_srchArea, &bp->bp_bbox);
if(inside)
{
bpe->bpe_top->bps_state = BPS_BINS_INSIDE;
}
else
{
bpe->bpe_top->bps_state = BPS_BINS;
bpe->bpe_subBinMinX = GEO_WIDTH(&bpe->bpe_srchArea)/2;
bpe->bpe_subBinMinY = GEO_HEIGHT(&bpe->bpe_srchArea)/2;
bpBinsUpdate(bp);
}
break;
default:
ASSERT(FALSE,"BPEnumInit, bad match value");
}
/* push rootnode */
if(bp->bp_rootNode)
{
bpEnumPush(bpe, bp->bp_rootNode, inside);
bpe->bpe_nextElement = NULL;
}
else
{
/* no bins, go straight to inbox */
bpe->bpe_top->bps_state = BPS_INBOX | inside;
bpe->bpe_nextElement = bp->bp_inBox;
}
}
/*
* ----------------------------------------------------------------------------
* BPEnumTerm --
*
* terminate enumeration
*
* ----------------------------------------------------------------------------
*/
void BPEnumTerm(BPEnum *bpe)
{
BPEnum **linkp;
/*
fprintf(stderr,"DEBUG bpEnumTerm, id=%s\n",
bpe->bpe_id);
*/
/* unlink */
linkp = &bpe->bpe_plane->bp_enums;
while(*linkp && *linkp != bpe) linkp = &(*linkp)->bpe_next;
ASSERT(*linkp==bpe,"BPEnumTerm");
*linkp = bpe->bpe_next;
}

View File

@ -1,537 +0,0 @@
// ************************************************************************
//
// Copyright (c) 1995-2002 Juniper Networks, Inc. All rights reserved.
//
// Permission is hereby granted, without written agreement and without
// license or royalty fees, to use, copy, modify, and distribute this
// software and its documentation for any purpose, provided that the
// above copyright notice and the following three paragraphs appear in
// all copies of this software.
//
// IN NO EVENT SHALL JUNIPER NETWORKS, INC. BE LIABLE TO ANY PARTY FOR
// DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES
// ARISING OUT OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF
// JUNIPER NETWORKS, INC. HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH
// DAMAGE.
//
// JUNIPER NETWORKS, INC. SPECIFICALLY DISCLAIMS ANY WARRANTIES,
// INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, AND
// NON-INFRINGEMENT.
//
// THE SOFTWARE PROVIDED HEREUNDER IS ON AN "AS IS" BASIS, AND JUNIPER
// NETWORKS, INC. HAS NO OBLIGATION TO PROVIDE MAINTENANCE, SUPPORT,
// UPDATES, ENHANCEMENTS, OR MODIFICATIONS.
//
// ************************************************************************
#ifndef _MAGIC__BPLANE__BPENUM_H
#define _MAGIC__BPLANE__BPENUM_H
/* bpEnum.h --
*
* inlined Search routines for bplanes (see also bpEnum.c)
*
*/
#include <stdio.h>
#include "utils/utils.h"
#include "utils/geometry.h"
#include "utils/geofast.h"
#include "bplane/bplane.h"
#include "bplane/bplaneInt.h"
extern void DumpRect(char *msg, Rect *r);
/* state machine states */
#define BPS_BINS 0
#define BPS_BINS_INSIDE 1
#define BPS_INBOX 2
#define BPS_INBOX_INSIDE 3
#define BPS_HASH 4
#define BPS_DONE 5
/* range code */
#define R_LEFT 1
#define R_RIGHT 2
#define R_BOT 4
#define R_TOP 8
/*
* ----------------------------------------------------------------------------
*
* bpBinArea -- compute area covered by given bin.
*
* Returns: bin area.
*
* ----------------------------------------------------------------------------
*/
static __inline__ Rect bpBinArea(BinArray *ba, int i)
{
int dimX = ba->ba_dimX;
int dx = ba->ba_dx;
int dy = ba->ba_dy;
int xi = i % dimX;
int yi = i / dimX;
Rect area;
area.r_xbot = ba->ba_bbox.r_xbot + dx*xi;
area.r_ybot = ba->ba_bbox.r_ybot + dy*yi;
area.r_xtop = area.r_xbot + dx;
area.r_ytop = area.r_ybot + dy;
return area;
}
/*
* ----------------------------------------------------------------------------
* bpEnumRange --
*
* Determine which edges of search area bin overlaps.
*
* (Used to make match checks as efficient as possible, for example if bin
* does not extend past srch area in any direction, no match checking is
* required)
*
* Returns: int encoding 'range'.
*
* ----------------------------------------------------------------------------
*/
static __inline__ int
bpEnumRange(Rect *bin, Rect *srch)
{
int range = 0;
if (bin->r_xbot < srch->r_xbot) range |= R_LEFT;
if (bin->r_xtop > srch->r_xtop) range |= R_RIGHT;
if (bin->r_ybot < srch->r_ybot) range |= R_BOT;
if (bin->r_ytop > srch->r_ytop) range |= R_TOP;
return range;
}
/*
* ----------------------------------------------------------------------------
* bpEnumMatchQ -
*
* Check if element intersects search area
*
* range specifies which search area boundaries the element
* can potentially extend beyond.
*
* We rely on the optimizing compiler to remove unnecessary checks
* based on compile time knowledge of range value.
*
* Returns: TRUE on match, FALSE otherwise.
*
* ----------------------------------------------------------------------------
*/
static __inline__ bool
bpEnumMatchQ(BPEnum *bpe, Element *e)
{
Rect *area = &bpe->bpe_srchArea;
Rect *r = &e->e_rect;
if(r->r_xtop < area->r_xbot) return FALSE;
if(r->r_xbot > area->r_xtop) return FALSE;
if(r->r_ytop < area->r_ybot) return FALSE;
if(r->r_ybot > area->r_ytop) return FALSE;
return TRUE;
}
/*
* ----------------------------------------------------------------------------
* bpEnumPushInside --
*
* called by bpEnumPush when the binarray is entirely inside the search area
*
* push a bin array onto an enum stack.
*
* ----------------------------------------------------------------------------
*/
static __inline__ bool bpEnumPushInside(BPEnum *bpe,
BinArray *ba)
{
BPStack *bps;
/* push stack */
++bpe->bpe_top;
bps = bpe->bpe_top;
bps->bps_node = ba;
bps->bps_state = BPS_BINS_INSIDE;
/* set up indices to scan entire bin array */
bps->bps_i = -1;
bps->bps_max = ba->ba_numBins;
return TRUE;
}
/*
* ----------------------------------------------------------------------------
* bpEnumPush --
*
* push a bin array onto an enum stack.
*
* normally returns TRUE, returns FALSE on (possible) state change.
*
* ----------------------------------------------------------------------------
*/
static __inline__ bool bpEnumPush(BPEnum *bpe,
BinArray *ba,
bool inside)
{
Rect area;
Rect *bbox;
int dx;
int dy;
BPStack *bps;
/*
fprintf(stderr,"DEBUG bpEnumPush, inside=%d\n", inside);
*/
/* special case inside */
if(inside) return bpEnumPushInside(bpe,ba);
bbox = &ba->ba_bbox;
if(GEO_SURROUND(&bpe->bpe_srchArea,bbox))
{
bpEnumPushInside(bpe,ba);
return FALSE; /* state change */
}
/* push stack */
++bpe->bpe_top;
bps = bpe->bpe_top;
bps->bps_node = ba;
bps->bps_state = BPS_BINS;
bps->bps_subbin = FALSE;
bps->bps_rejects = 0;
/* compute search area for this bin array */
dx = ba->ba_dx;
dy = ba->ba_dy;
area.r_xbot = bpe->bpe_srchArea.r_xbot - dx;
area.r_xtop = bpe->bpe_srchArea.r_xtop + 1;
area.r_ybot = bpe->bpe_srchArea.r_ybot - dy;
area.r_ytop = bpe->bpe_srchArea.r_ytop + 1;
GEOCLIP(&area,bbox);
if(GEO_RECTNULL(&area))
{
/* only need to check oversized */
bps->bps_i = 0;
bps->bps_rowMax = 0;
bps->bps_max = 0;
}
else
{
/* setup indices for this array and search area */
int dimX = ba->ba_dimX;
int i;
/* make area relative to bin bbox */
area.r_xbot -= bbox->r_xbot;
area.r_xtop -= bbox->r_xbot;
area.r_ybot -= bbox->r_ybot;
area.r_ytop -= bbox->r_ybot;
/* DumpRect("area relative to bin bbox = ",&area); */
area.r_xbot /= ba->ba_dx;
area.r_xtop /= ba->ba_dx;
area.r_ybot /= ba->ba_dy;
area.r_ytop /= ba->ba_dy;
i = area.r_ybot*dimX + area.r_xbot; /* next index */
bps->bps_i = i-1;
bps->bps_rowMax = i + area.r_xtop - area.r_xbot;
bps->bps_max = area.r_ytop*dimX + area.r_xtop;
bps->bps_rowDelta = dimX + area.r_xbot - area.r_xtop;
bps->bps_dimX = dimX;
/* consider subbinning? */
if(dx >= bpe->bpe_subBinMinX || dy >= bpe->bpe_subBinMinY)
{
bps->bps_subbin = TRUE;
}
}
return TRUE;
}
/*
* ----------------------------------------------------------------------------
* bpEnumNextBin1 --
*
* called by bpEnumNextBin() after indexes for new bin are setup
*
* returns: normally returns TRUE, returns FALSE on state change.
*
* ----------------------------------------------------------------------------
*/
static __inline__ bool
bpEnumNextBin1(BPEnum *bpe, BPStack *bps, bool inside)
{
if(bpBinType(bps->bps_node,bps->bps_i) != BT_ARRAY)
{
bpe->bpe_nextElement = bpBinList(bps->bps_node,bps->bps_i);
return TRUE;
}
/* array, push into it */
return bpEnumPush(bpe, bpSubArray(bps->bps_node,bps->bps_i), inside);
}
/*
* ----------------------------------------------------------------------------
* bpEnumNextBin --
*
* called by bpEnumNextBINS to advance to next bin (bucket).
*
* cycles through normal bins first, then oversized,
* finally, for toplevel, sets INBOX state.
*
* sets bpe->bpe_nextElement to first element in next bin.
*
* returns: normally returns TRUE, returns FALSE on state change.
*
* ----------------------------------------------------------------------------
*/
static __inline__ bool
bpEnumNextBin(BPEnum *bpe, bool inside)
{
BPStack *bps = bpe->bpe_top;
#ifdef BPARANOID
ASSERT(bps,"bpEnumNextBin");
ASSERT(!bpe->bpe_nextElement,"bpEnumNextBin");
#endif
/*
fprintf(stderr,"DEBUG bpEnumNextBin TOP inside=%d nextElement=%x\n",
inside, bpe->bpe_nextElement);
*/
/* consider subbining this bin before advancing to next */
if(!inside)
{
if(bps->bps_rejects >= bpMinBAPop
&& (bps->bps_subbin || bps->bps_i == bps->bps_node->ba_numBins))
{
int i = bps->bps_i;
BinArray *ba = bps->bps_node;
BinArray *sub;
/* fprintf(stderr,"DEBUG, subbining!\n"); */
sub = bpBinArrayBuild(bpBinArea(ba,i),
bpBinList(ba,i),
FALSE); /* don't recursively subbin! */
if(sub)
{
ba->ba_bins[i] =
(void *) ((pointertype) sub | BT_ARRAY);
}
}
bps->bps_rejects = 0;
}
/* handle inside case first */
if(inside)
{
/* Inside case, cycle through all bins */
/* next bin */
if(bps->bps_i<bps->bps_max)
{
bps->bps_i += 1;
return bpEnumNextBin1(bpe,bps,inside);
}
}
else
{
/* cycle only through relevant bins */
/* next in row */
if(bps->bps_i<bps->bps_rowMax)
{
bps->bps_i += 1;
goto bin;
}
/* next row */
if(bps->bps_i<bps->bps_max)
{
bps->bps_i += bps->bps_rowDelta;
bps->bps_rowMax += bps->bps_dimX;
goto bin;
}
/* oversized */
if(bps->bps_i == bps->bps_max)
{
bps->bps_i = bps->bps_node->ba_numBins;
goto bin;
}
}
/* pop stack */
/* fprintf(stderr,"DEBUG BPEnumNextBin Pop.\n"); */
bpe->bpe_top--;
if(bpe->bpe_top>bpe->bpe_stack) return FALSE; /* state may have changed */
/* inbox */
/* fprintf(stderr,"DEBUG BPEnumNextBin INBOX.\n"); */
bpe->bpe_nextElement = bpe->bpe_plane->bp_inBox;
bpe->bpe_top->bps_state = BPS_INBOX | inside;
return FALSE; /* state change */
/* dive into indexed bin */
bin:
return bpEnumNextBin1(bpe,bps,inside);
}
/*
* ----------------------------------------------------------------------------
* bpEnumNextBINS --
*
* Handle BINS state for BPEnumNext()
*
* (bin enumeration.)
*
* ----------------------------------------------------------------------------
*/
static __inline__ Element* bpEnumNextBINS(BPEnum *bpe, bool inside)
{
/* bin by bin */
do
{
/* search this bin */
Element *e = bpe->bpe_nextElement;
while(e && !inside && !bpEnumMatchQ(bpe,e))
{
bpe->bpe_top->bps_rejects++;
e = e->e_link;
}
if(e)
{
bpe->bpe_nextElement = e->e_link;
/* DumpRect("DEBUG e_rect= ",&e->e_rect); */
return e;
}
bpe->bpe_nextElement = NULL;
}
while(bpEnumNextBin(bpe,inside));
/* next state */
return NULL;
}
/*
* ----------------------------------------------------------------------------
* bpEnumNextINBOX --
*
* Handle INBOX states for BPEnumNext()
*
* unbinned enumeration.
*
* ----------------------------------------------------------------------------
*/
static __inline__ Element *bpEnumNextINBOX(BPEnum *bpe,
bool inside)
{
Element *e = bpe->bpe_nextElement;
while(e && !inside && !bpEnumMatchQ(bpe,e)) e = e->e_link;
if(e)
{
bpe->bpe_nextElement = e->e_link;
return e;
}
/* done */
bpe->bpe_top->bps_state = BPS_DONE;
return NULL;
}
/*
* ----------------------------------------------------------------------------
* bpEnumNextHASH --
*
* Handle HASH state for BPEnumNext()
*
* (hash based (EQUALS) enumerations.)
*
* ----------------------------------------------------------------------------
*/
static __inline__ Element *bpEnumNextHASH(BPEnum *bpe)
{
Element *e = bpe->bpe_nextElement;
if(e)
{
bpe->bpe_nextElement =
IHashLookUpNext(bpe->bpe_plane->bp_hashTable, e);
}
else
{
bpe->bpe_top->bps_state = BPS_DONE;
}
return e;
}
/*
* ----------------------------------------------------------------------------
* BPEnumNext --
*
* get next element in enumeration.
*
* ----------------------------------------------------------------------------
*/
static __inline__ void *BPEnumNext(BPEnum *bpe)
{
Element *e;
while(TRUE)
{
/*
fprintf(stderr,"DEBUG state=%d\n",bpe->bpe_top->bps_state);
*/
switch (bpe->bpe_top->bps_state)
{
case BPS_BINS:
if((e=bpEnumNextBINS(bpe, 0))) return e;
break;
case BPS_BINS_INSIDE:
if((e=bpEnumNextBINS(bpe, 1))) return e;
break;
case BPS_INBOX:
if((e=bpEnumNextINBOX(bpe, 0))) return e;
break;
case BPS_INBOX_INSIDE:
if((e=bpEnumNextINBOX(bpe, 1))) return e;
break;
case BPS_HASH:
if((e=bpEnumNextHASH(bpe))) return e;
break;
case BPS_DONE:
return NULL;
default:
ASSERT(FALSE,"BPEnumNext, bad state");
}
}
}
#endif /* _MAGIC__BPLANE__BPENUM_H */

View File

@ -1,280 +0,0 @@
// ************************************************************************
//
// Copyright (c) 1995-2002 Juniper Networks, Inc. All rights reserved.
//
// Permission is hereby granted, without written agreement and without
// license or royalty fees, to use, copy, modify, and distribute this
// software and its documentation for any purpose, provided that the
// above copyright notice and the following three paragraphs appear in
// all copies of this software.
//
// IN NO EVENT SHALL JUNIPER NETWORKS, INC. BE LIABLE TO ANY PARTY FOR
// DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES
// ARISING OUT OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF
// JUNIPER NETWORKS, INC. HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH
// DAMAGE.
//
// JUNIPER NETWORKS, INC. SPECIFICALLY DISCLAIMS ANY WARRANTIES,
// INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, AND
// NON-INFRINGEMENT.
//
// THE SOFTWARE PROVIDED HEREUNDER IS ON AN "AS IS" BASIS, AND JUNIPER
// NETWORKS, INC. HAS NO OBLIGATION TO PROVIDE MAINTENANCE, SUPPORT,
// UPDATES, ENHANCEMENTS, OR MODIFICATIONS.
//
// ************************************************************************
/* bpMain.c
*
* Top-level routines for BPlanes
* (interface to other modules)
*
* See bpEnum.c for enum routines.
* See bpTcl.c for tcl-level interface.
*/
#include <stdio.h>
#include <stddef.h>
#include "utils/utils.h"
#include "utils/malloc.h"
#include "database/database.h"
#include "textio/textio.h"
#include "utils/geometry.h"
#include "bplane/bplaneInt.h"
/*
* ----------------------------------------------------------------------------
* BPNew --
*
* Return newly created BPlane.
*
* ----------------------------------------------------------------------------
*/
BPlane *BPNew(void)
{
BPlane *new;
new = (BPlane *)mallocMagic(sizeof(BPlane));
new->bp_bbox = GeoNullRect;
new->bp_bbox_exact = TRUE;
new->bp_count = 0;
/* ENUMS */
new->bp_enums = NULL;
/* HASH TABLE */
new->bp_hashTable = IHashInit(4, /* initial buckets */
offsetof(Element, e_rect), /* key */
offsetof(Element, e_hashLink),
IHash4WordKeyHash,
IHash4WordKeyEq);
/* IN BOX */
new->bp_inBox = NULL;
/* BINS */
new->bp_binLife = 0;
new->bp_inAdds = 0;
new->bp_binArea = GeoNullRect;
new->bp_rootNode = NULL;
return new;
}
/*
* ----------------------------------------------------------------------------
* BPFree --
*
* free (empty) BPlane
*
* ----------------------------------------------------------------------------
*/
void BPFree(BPlane *bp)
{
ASSERT(bp->bp_count == 0,"BPFree");
IHashFree(bp->bp_hashTable);
freeMagic((char *)bp);
}
/*
* ----------------------------------------------------------------------------
* BPAdd --
*
* Add element to the given bplane
*
* NOTE: e_rect better be canonical!
*
* ----------------------------------------------------------------------------
*/
void BPAdd(BPlane *bp, void *element)
{
int size;
int binDim;
Element * e = element;
Rect *r = &e->e_rect;
/* Don't allow adds during active enumerations.
* This is confusing, since newly added elements may or may not
* be enumerated in on going enumerations, is not particularly
* useful, since elements to add can just be stored up on a local
* list and added after the enumeration completes.
*/
ASSERT(!bp->bp_enums,
"BPAdd, attempted during active enumerations");
/* element rect must be canonical! */
#ifdef BPARANOID
ASSERT(GeoIsCanonicalRect(r),"BPAdd, rect must be canonical.");
#endif
bp->bp_count++;
/* update hash table */
IHashAdd(bp->bp_hashTable, element);
/* update bbox */
if(bp->bp_count == 1)
{
bp->bp_bbox = *r;
}
else
{
GeoIncludeRectInBBox(r,&bp->bp_bbox);
}
/* no bins? */
if(!bp->bp_rootNode) goto inBox;
/* doesn't fit inside bins ? */
if(!GEO_SURROUND(&bp->bp_binArea,r)) goto inBox;
/* bin element */
bpBinAdd(bp->bp_rootNode, e);
return;
/* add to in box */
inBox:
bp->bp_inAdds++;
e->e_link = bp->bp_inBox;
bp->bp_inBox = e;
/* maintain back pointers */
e->e_linkp = &bp->bp_inBox;
if(e->e_link) e->e_link->e_linkp = &e->e_link;
}
/*
* ----------------------------------------------------------------------------
* BPDelete --
*
* remove element from bplane
*
* ----------------------------------------------------------------------------
*/
void BPDelete(BPlane *bp, void *element)
{
Element *e = element;
ASSERT(e,"BPDelete");
if (bp->bp_count == 0)
{
TxError("Error: Attempt to delete instance from empty cell!\n");
return;
}
bp->bp_count--;
/* if element was on edge of bbox, bbox may no longer
* be exact.
*/
if(bp->bp_bbox_exact &&
(bp->bp_bbox.r_xbot == e->e_rect.r_xbot ||
bp->bp_bbox.r_xtop == e->e_rect.r_xtop ||
bp->bp_bbox.r_ybot == e->e_rect.r_ybot ||
bp->bp_bbox.r_ytop == e->e_rect.r_ytop))
{
bp->bp_bbox_exact = FALSE;
}
/* advance any nextElement pointers at e */
{
BPEnum *bpe;
for(bpe=bp->bp_enums; bpe; bpe=bpe->bpe_next)
{
if(bpe->bpe_nextElement != e) continue;
if(bpe->bpe_match == BPE_EQUAL)
{
bpe->bpe_nextElement = IHashLookUpNext(bp->bp_hashTable, e);
}
else
{
bpe->bpe_nextElement = e->e_link;
}
}
}
IHashDelete(bp->bp_hashTable, e);
/* next pointer of prev element */
*e->e_linkp = e->e_link;
/* back pointer of next element */
if(e->e_link) e->e_link->e_linkp = e->e_linkp;
}
/*
* ----------------------------------------------------------------------------
* BPBBox --
*
* Get current bplane bbox.
*
* returns: current bplane bbox
* (returns an inverted rect, if bplane is empty)
*
* ----------------------------------------------------------------------------
*/
Rect BPBBox(BPlane *bp)
{
if(bp->bp_count == 0) return GeoInvertedRect;
/* if bbox is not up-to-date, recompute */
if(!bp->bp_bbox_exact)
{
BPEnum bpe;
Element *e;
bp->bp_bbox_exact = TRUE;
BPEnumInit(&bpe,
bp,
NULL,
BPE_ALL,
"BPBBox");
e = BPEnumNext(&bpe);
bp->bp_bbox = e->e_rect;
while((e = BPEnumNext(&bpe)))
{
GeoIncludeRectInBBox(&e->e_rect, &bp->bp_bbox);
}
}
return bp->bp_bbox;
}

View File

@ -1,195 +0,0 @@
// ************************************************************************
//
// Copyright (c) 1995-2002 Juniper Networks, Inc. All rights reserved.
//
// Permission is hereby granted, without written agreement and without
// license or royalty fees, to use, copy, modify, and distribute this
// software and its documentation for any purpose, provided that the
// above copyright notice and the following three paragraphs appear in
// all copies of this software.
//
// IN NO EVENT SHALL JUNIPER NETWORKS, INC. BE LIABLE TO ANY PARTY FOR
// DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES
// ARISING OUT OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF
// JUNIPER NETWORKS, INC. HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH
// DAMAGE.
//
// JUNIPER NETWORKS, INC. SPECIFICALLY DISCLAIMS ANY WARRANTIES,
// INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, AND
// NON-INFRINGEMENT.
//
// THE SOFTWARE PROVIDED HEREUNDER IS ON AN "AS IS" BASIS, AND JUNIPER
// NETWORKS, INC. HAS NO OBLIGATION TO PROVIDE MAINTENANCE, SUPPORT,
// UPDATES, ENHANCEMENTS, OR MODIFICATIONS.
//
// ************************************************************************
#ifndef _MAGIC__BPLANE__BPOPAQUE_H
#define _MAGIC__BPLANE__BPOPAQUE_H
#ifndef _MAGIC__UTILS__IHASH_H
#include "utils/ihash.h"
#endif
/*
* bpOpaque.h --
*
* This file contains strucs directly or indirectly referenced by
* clients of bplane module, whose internals should be treated
* as opaque by clients.
*
* It is included by bplane.h
*
*/
/* data element, stored in BPlane
*
* Storage managed by caller.
* Inital part must correspond to below.
*/
typedef struct element
{
struct element *e_hashLink;
struct element *e_link;
struct element **e_linkp; /* back pointer for quick deletes */
Rect e_rect;
/* client data goes here */
} Element;
/* number of link fields in element
*
* user code should not depend on more than 1 link.
* (and should only use/ref that link when element is not in a bplane)
*/
#define BP_NUM_LINKS 3
/* bin array */
typedef struct binarray
{
Rect ba_bbox; /* area covered by array */
int ba_dx; /* dimensions of a single bin */
int ba_dy;
int ba_dimX; /* number of bins in a row */
int ba_numBins; /* number of regular bins (size of array - 1) */
void *ba_bins[1]; /* low order bit(s) used to encode type info.
* DON'T ACCESS DIRECTLY, USE MACROS BELOW
*
* (last bin is for oversized)
*/
} BinArray;
/* bin types
*
* NOTE: its important that simple lists have type 0, i.e. are
* just standard pointers. This is so that the list head
* 'link' can be treated just as any other link, during
* deletion etc.
*/
#define BT_TYPE_MASK 1
#define BT_LIST 0
#define BT_ARRAY 1
static __inline__ bool bpBinEmpty(BinArray *ba, int i)
{
return ba->ba_bins[i] == NULL;
}
static __inline__ bool bpBinType(BinArray *ba, int i)
{
return (bool) (((pointertype) ba->ba_bins[i]) & BT_TYPE_MASK);
}
static __inline__ Element *bpBinList(BinArray *ba, int i)
{
#ifdef BPARANOID
ASSERT(bpBinType(ba,i)==BT_LIST,"bpBinList");
#endif
return (Element *) ba->ba_bins[i];
}
static __inline__ Element **bpBinListHead(BinArray *ba, int i)
{
#ifdef BPARANOID
ASSERT(bpBinType(ba,i)==BT_LIST,"bpBinList");
#endif
return (Element **) &ba->ba_bins[i];
}
static __inline__ BinArray *bpSubArray(BinArray *ba, int i)
{
#ifdef BPARANOID
ASSERT(bpBinType(ba,i)==BT_ARRAY,"bpSubArray");
#endif
return (BinArray *) ((pointertype) ba->ba_bins[i] & ~BT_TYPE_MASK);
}
/* BPlane - toplevel struc */
typedef struct bplane
{
Rect bp_bbox; /* bbox (bin + in) */
bool bp_bbox_exact; /* if set bp_bbox, is exact,
* if reset bp_bbox may be over-sized.
*/
int bp_count; /* total number of elements in bplane */
struct bpenum *bp_enums; /* list of active enums */
/* HASH TABLE */
IHashTable *bp_hashTable; /* hash table
* (for expediting BP_EQUAL searches) */
/* IN BOX */
Element *bp_inBox; /* elements not yet added to bin system */
/* BINS */
int bp_binLife; /* set to binCount when bin system
* built, decremented on add/delete ops.
* bin system rebuilt when zero reached.
*/
int bp_inAdds; /* additions to inBox since last rebuild */
Rect bp_binArea; /* area covered by bin arrays */
BinArray *bp_rootNode; /* top bin node */
} BPlane;
/* context for BPlane enumeration */
typedef struct bpStack
{
int bps_state; /* where we are at rolled in one convenient
* number (see BPS_* defs in bpEnum.h)
*/
BinArray *bps_node; /* current bin array */
int bps_i; /* current index */
int bps_rowMax; /* max index for this row */
int bps_rowDelta; /* increment from end of one row to beginning
* of next.
*/
int bps_max; /* max index */
int bps_dimX; /* row length */
bool bps_subbin; /* if set consider subbinning */
int bps_rejects; /* number of unmatching elements in current
* bin, used to decide when to subbin.
*/
} BPStack;
/* enumeration 'handle' */
typedef struct bpenum
{
struct bpenum *bpe_next; /* all enums for bplane linked together */
BPlane *bpe_plane; /* plane being searched */
Rect bpe_srchArea; /* area being searched */
int bpe_match; /* match criteria */
const char *bpe_id; /* for debug */
int bpe_subBinMinX;
int bpe_subBinMinY; /* consider subbinning
* for bins bigger than this.
*/
Element *bpe_nextElement; /* next element in current list */
BPStack *bpe_top; /* top of stack */
BPStack bpe_stack[10000]; /* stack for tree traversal during enum */
} BPEnum;
#endif /* _MAGIC__BPLANE__BPOPAQUE_H */

View File

@ -1,304 +0,0 @@
// ************************************************************************
//
// Copyright (c) 1995-2002 Juniper Networks, Inc. All rights reserved.
//
// Permission is hereby granted, without written agreement and without
// license or royalty fees, to use, copy, modify, and distribute this
// software and its documentation for any purpose, provided that the
// above copyright notice and the following three paragraphs appear in
// all copies of this software.
//
// IN NO EVENT SHALL JUNIPER NETWORKS, INC. BE LIABLE TO ANY PARTY FOR
// DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES
// ARISING OUT OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF
// JUNIPER NETWORKS, INC. HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH
// DAMAGE.
//
// JUNIPER NETWORKS, INC. SPECIFICALLY DISCLAIMS ANY WARRANTIES,
// INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, AND
// NON-INFRINGEMENT.
//
// THE SOFTWARE PROVIDED HEREUNDER IS ON AN "AS IS" BASIS, AND JUNIPER
// NETWORKS, INC. HAS NO OBLIGATION TO PROVIDE MAINTENANCE, SUPPORT,
// UPDATES, ENHANCEMENTS, OR MODIFICATIONS.
//
// ************************************************************************
/* bpStat.c
*
* routines to get bplane statistics.
*
*/
#include <stdio.h>
#include <limits.h>
#include "utils/utils.h"
#include "database/database.h"
#include "utils/geometry.h"
#include "bplane/bplaneInt.h"
/*
* ----------------------------------------------------------------------------
* bpCount --
*
* count list of elements.
*
* Returns size of list.
*
* ----------------------------------------------------------------------------
*/
int bpCount(Element *e)
{
int i = 0;
while(e)
{
i++;
e = e->e_link;
}
return i;
}
/*
* ----------------------------------------------------------------------------
* bpStatBA --
*
* compute bin array statistics.
* (includes sub-arrays)
*
*
* Returns memory used by bplane (excluding elements)
*
* ----------------------------------------------------------------------------
*/
unsigned int bpStatBA(BinArray *ba,
int *totCount, /* total number of elements */
int *totBins, /* ret tot num of bins */
int *emptyBins, /* ret num of empty bins */
int *binArraysp, /* ret num of bin arrays */
int *maxEffp, /* ret max effective list length */
int *maxBinCount, /* ret max count for regular bin */
int *totUnbinned, /* ret tot num of e's not binned */
int *maxDepth) /* ret max bin array depth */
{
Rect *bbox = &ba->ba_bbox;
int dx = ba->ba_dx;
int dy = ba->ba_dy;
int numBins = ba->ba_numBins;
int dimX = ba->ba_dimX;
int dimY = numBins/dimX;
int w = GEO_WIDTH(bbox);
int h = GEO_HEIGHT(bbox);
/* initial statistics */
unsigned int mem = 0;
int tot = 0;
int bins = 0;
int emptys = 0;
int binArrays = 1;
int maxCount = 0;
int maxEff = 0;
int maxEffSub = 0;
int maxSubCount = 0;
int unbinned = 0;
int depth = 1;
int maxDepthSub = 0;
int i;
/* add bins in this array */
bins += numBins;
/* add memory usage for this array (sub arrays already tabulated) */
if(ba) mem += sizeof(BinArray) + numBins*sizeof(void*);
/* gather stats bin by bin */
for(i=0;i<numBins;i++)
{
if(bpBinType(ba,i) != BT_ARRAY)
{
/* simple bin */
int count = bpCount(bpBinList(ba,i));
tot += count;
if(count>maxCount) maxCount = count;
if(count==0) emptys++;
}
else
{
/* arrayed, recurse */
int sMem, sTot, sBins, sEmptys, sBinArrays;
int sMaxEff, sMaxCount, sUnbinned, sDepth;
sMem = bpStatBA(bpSubArray(ba,i),
&sTot, /* total number of elements */
&sBins, /* ret tot num of bins */
&sEmptys, /* ret num of empty bins */
&sBinArrays, /* ret num bin arrays */
&sMaxEff, /* ret max effective list length */
&sMaxCount, /* ret max count for regular bin */
&sUnbinned, /* ret tot num of e's not binned */
&sDepth); /* ret max bin array depth */
mem += sMem;
tot += sTot;
bins += sBins;
emptys += sEmptys;
binArrays += sBinArrays;
if(sMaxEff > maxEffSub) maxEffSub = sMaxEff;
if(sMaxCount > maxCount) maxCount = sMaxCount;
if(sUnbinned > maxCount) maxCount = sUnbinned;
if(sDepth > maxDepthSub) maxDepthSub = sDepth;
}
}
maxEff += MAX(maxCount,maxEffSub);
depth += maxDepthSub;
/* oversized */
if(bpBinType(ba,numBins) != BT_ARRAY)
{
/* oversized unbinned */
int over = bpCount(bpBinList(ba,numBins));
tot += over;
unbinned += over;
maxEff += over;
}
else
{
/* oversized is arrayed, recurse */
int sMem, sTot, sBins, sEmptys, sBinArrays;
int sMaxEff, sMaxCount, sUnbinned, sDepth;
sMem = bpStatBA(bpSubArray(ba,numBins),
&sTot, /* total number of elements */
&sBins, /* ret tot num of bins */
&sEmptys, /* ret num of empty bins */
&sBinArrays, /* ret num bin arrays */
&sMaxEff, /* ret max effective list length */
&sMaxCount, /* ret max count for regular bin */
&sUnbinned, /* ret tot num of e's not binned */
&sDepth); /* ret max bin array depth */
mem += sMem;
tot += sTot;
bins += sBins;
emptys += sEmptys;
binArrays += sBinArrays;
maxEff += sMaxEff;
if(sMaxCount > maxCount) maxCount = sMaxCount;
unbinned += sUnbinned;
depth += sDepth;
}
/* set results */
if(totCount) *totCount = tot;
if(totBins) *totBins = bins;
if(emptyBins) *emptyBins = emptys;
if(binArraysp) *binArraysp = binArrays;
if(maxEffp) *maxEffp = maxEff;
if(maxBinCount) *maxBinCount = maxCount;
if(totUnbinned) *totUnbinned = unbinned;
if(maxDepth) *maxDepth = depth;
return mem;
}
/*
* ----------------------------------------------------------------------------
* BPStat --
*
* compute bplane statistics.
*
* Returns memory used by bplane (excluding elements)
*
* ----------------------------------------------------------------------------
*/
unsigned int BPStat(BPlane *bp,
int *totCount, /* total number of elements */
int *inBox, /* ret num of elements in inBox */
int *totBins, /* ret tot num of bins */
int *emptyBins, /* ret num of empty bins */
int *binArraysp, /* ret tot num of bin arrays */
int *maxEffp, /* ret max effective list length */
int *maxBinCount, /* ret max count for regular bin */
int *totUnbinned, /* ret tot num of e's not binned */
int *maxDepth) /* ret max bin array depth */
{
BinArray *ba = bp->bp_rootNode;
int numBins;
unsigned int mem = 0;
int tot = 0;
int bins = 0;
int emptys = 0;
int binArrays = 0;
int maxEff = 0;
int maxCount = 0;
int unbinned = 0;
int depth = 0;
int in;
/* bin arrays */
if(ba)
{
mem += bpStatBA(bp->bp_rootNode,
&tot, /* total number of elements */
&bins, /* ret tot num of bins */
&emptys, /* ret tot num of empty bins */
&binArrays, /* ret tot num of bin arrays */
&maxEff, /* ret max effective list length */
&maxCount, /* ret max count for regular bin */
&unbinned, /* ret tot num of e's not binned */
&depth); /* ret max bin array depth */
}
/* inbox */
in = bpCount(bp->bp_inBox);
tot += in;
maxEff += in;
unbinned += in;
/* add in memory usage for bplane */
mem += sizeof(BPlane);
mem += IHashStats2(bp->bp_hashTable,NULL,NULL);
/* set results */
if(totCount) *totCount = tot;
if(inBox) *inBox = in;
if(totBins) *totBins = bins;
if(emptyBins) *emptyBins = emptys;
if(binArraysp) *binArraysp = binArrays;
if(maxEffp) *maxEffp = maxEff;
if(maxBinCount) *maxBinCount = maxCount;
if(totUnbinned) *totUnbinned = unbinned;
if(maxDepth) *maxDepth = depth;
return mem;
}
/*
* ----------------------------------------------------------------------------
* BPStatMemory --
*
* returns memory usage of BPlane in bytes
* (exclusive of elements contained by the BPlane)
*
* ----------------------------------------------------------------------------
*/
unsigned int BPStatMemory(BPlane *bp)
{
return BPStat(bp,
NULL,
NULL,
NULL,
NULL,
NULL,
NULL,
NULL,
NULL,
NULL);
}

View File

@ -1,361 +0,0 @@
// ************************************************************************
//
// Copyright (c) 1995-2002 Juniper Networks, Inc. All rights reserved.
//
// Permission is hereby granted, without written agreement and without
// license or royalty fees, to use, copy, modify, and distribute this
// software and its documentation for any purpose, provided that the
// above copyright notice and the following three paragraphs appear in
// all copies of this software.
//
// IN NO EVENT SHALL JUNIPER NETWORKS, INC. BE LIABLE TO ANY PARTY FOR
// DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES
// ARISING OUT OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF
// JUNIPER NETWORKS, INC. HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH
// DAMAGE.
//
// JUNIPER NETWORKS, INC. SPECIFICALLY DISCLAIMS ANY WARRANTIES,
// INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, AND
// NON-INFRINGEMENT.
//
// THE SOFTWARE PROVIDED HEREUNDER IS ON AN "AS IS" BASIS, AND JUNIPER
// NETWORKS, INC. HAS NO OBLIGATION TO PROVIDE MAINTENANCE, SUPPORT,
// UPDATES, ENHANCEMENTS, OR MODIFICATIONS.
//
// ************************************************************************
/* bpTest.c
*
* (regression) tests of bplane code
*
*/
#include <stdio.h>
#include <stdlib.h>
#include "utils.h"
#include "message.h"
#include "database.h"
#include "geometry.h"
#include "bplane.h"
#include "bplaneInt.h"
#include "debug.h"
#include "cifInt.h"
/*
* elements used by test code.
*/
typedef struct rectc
{
struct rectc *rc_links[BP_NUM_LINKS];
Rect rc_rect;
} RectC;
/*
* ----------------------------------------------------------------------------
* bpRand --
* generate a random int in given range.
*
* side effects: sets coords of input rect.
* ----------------------------------------------------------------------------
*/
int bpRand(int min, int max)
{
double f = rand()/ (double) RAND_MAX; /* random number in unit interval */
return min + (int) ((max-min+1)*f);
}
/*
* ----------------------------------------------------------------------------
* bpTestRandRect --
* generate a random unit rectangle inside bbox
*
* side effects: sets coords of input rect.
* ----------------------------------------------------------------------------
*/
static void bpTestRandRect(Rect *r, Rect *bbox)
{
r->r_xbot = bpRand(bbox->r_xbot,bbox->r_xtop-1);
r->r_ybot = bpRand(bbox->r_ybot,bbox->r_ytop-1);
r->r_xtop = r->r_xbot+1;
r->r_ytop = r->r_ybot+1;
}
/* ====== GOLD snow test.
* ====== linked list implementation (to determine 'right' answer)
*/
/*
* ----------------------------------------------------------------------------
* bpTestIntersectGold --
*
* check whether rc intersects list
* ----------------------------------------------------------------------------
*/
static bool bpTestIntersectGold(RectC *rc, RectC *list)
{
while(list)
{
if(GEO_TOUCH(&rc->rc_rect,&list->rc_rect)) return TRUE;
list=list->rc_links[0];
}
return FALSE;
}
/*
* ----------------------------------------------------------------------------
* bpTestSnowGold --
* populate square of dimension 'size' with non-overlapping random unit
* rectangles. Keep adding rectangles until failures exceed successes.
* (stop when maxFailures reached.)
*
* coded with simple linked list.
*
* ---------------------------------------------------------------------------- */
void bpTestSnowGold(int size, bool trace)
{
int failures = 0;
int successes = 0;
int i = 0;
int crc = 0;
RectC *result = NULL;
RectC *rc = NULL;
Rect area;
fprintf(stderr,"BEGIN Snow GOLD, size=%d\n", size);
/* set up area */
area.r_xbot = 0;
area.r_ybot = 0;
area.r_xtop = size;
area.r_ytop = size;
while(failures<=successes)
{
i++;
if(!rc) rc = MALLOC_TAG(RectC *,rc, sizeof(RectC), "RectC");
bpTestRandRect(&rc->rc_rect, &area);
if(!bpTestIntersectGold(rc,result))
{
if(trace) DumpRect("success ",&rc->rc_rect);
crc ^= i+ 3*rc->rc_rect.r_xbot+ 5*rc->rc_rect.r_ybot;
rc->rc_links[0] = result;
result = rc;
rc = NULL;
successes++;
}
else
{
if(trace) DumpRect("failure ",&rc->rc_rect);
failures++;
}
}
/* clean up */
while(result)
{
/* pop */
rc=result;
result=rc->rc_links[0];
/* free */
FREE(rc);
}
fprintf(stderr,"END Snow GOLD, size=%d failures=%d successes=%d crc=%d\n",
size,
failures,
successes,
crc);
}
/* ====== bplane snow test.
*/
/*
* ----------------------------------------------------------------------------
* bpTestIntersect --
*
* check whether rc intersects list
* ----------------------------------------------------------------------------
*/
static bool bpTestIntersect(RectC *rc, BPlane *bp)
{
BPEnum bpe;
int result;
BPEnumInit(&bpe,bp, &rc->rc_rect, BPE_TOUCH,"bpTestIntersect");
result = (BPEnumNext(&bpe)!=NULL);
BPEnumTerm(&bpe);
return result;
}
/*
* ----------------------------------------------------------------------------
* bpTestSnow --
* populate area with non-overlapping random unit rectangles.
*
* using bplane.
*
* ----------------------------------------------------------------------------
*/
BPlane *bpTestSnow(int size, bool trace)
{
int failures = 0;
int successes = 0;
int i = 0;
int crc = 0;
RectC *result = NULL;
RectC *rc = NULL;
BPlane *bp = BPNew();
Rect area;
fprintf(stderr,"BEGIN Snow, size=%d\n", size);
/* set up area */
area.r_xbot = 0;
area.r_ybot = 0;
area.r_xtop = size;
area.r_ytop = size;
while(failures<=successes)
{
i++;
if(!rc) rc = MALLOC_TAG(RectC *,rc, sizeof(RectC), "RectC");
bpTestRandRect(&rc->rc_rect, &area);
if(!bpTestIntersect(rc,bp))
{
if(trace) DumpRect("success ",&rc->rc_rect);
crc ^= i+ 3*rc->rc_rect.r_xbot+ 5*rc->rc_rect.r_ybot;
BPAdd(bp,rc);
rc = NULL;
successes++;
}
else
{
if(trace) DumpRect("failure ",&rc->rc_rect);
failures++;
}
}
fprintf(stderr,"END Snow, size=%d failures=%d success=%d crc=%d\n",
size,
failures,
successes,
crc);
return bp;
}
/* ====== Tile Plane based snow test.
*/
/*
* ----------------------------------------------------------------------------
* bpTestIntersectTile --
*
* check whether r intersects existing tiles
*
* ----------------------------------------------------------------------------
*/
int bpTestIntersectTileFunc(Tile *tile, ClientData cd)
{
return 1;
}
static bool bpTestIntersectTile(Rect *r, Plane *plane)
{
Rect area;
/* catch touching tiles */
area = *r;
area.r_xbot -= 1;
area.r_ybot -= 1;
area.r_xtop += 1;
area.r_ytop += 1;
return DBPlaneEnumAreaPaint((Tile *) NULL,
plane,
&area,
&DBAllButSpaceBits,
bpTestIntersectTileFunc,
NULL);
}
/*
* ----------------------------------------------------------------------------
* bpTestSnowTile --
* populate area with non-overlapping random unit rectangles.
*
* using tile plane
*
* ----------------------------------------------------------------------------
*/
Plane *bpTestSnowTile(int size, bool trace)
{
int failures = 0;
int successes = 0;
int i = 0;
int crc = 0;
RectC *result = NULL;
RectC *rc = NULL;
Plane *plane = DBPlaneNew((ClientData) TT_SPACE);
Rect area;
fprintf(stderr,"BEGIN Snow Tile, size=%d\n", size);
/* set up area */
area.r_xbot = 0;
area.r_ybot = 0;
area.r_xtop = size;
area.r_ytop = size;
while(failures<=successes)
{
Rect r;
i++;
bpTestRandRect(&r, &area);
if(!bpTestIntersectTile(&r,plane))
{
if(trace) DumpRect("success ",&r);
crc ^= i+ 3*r.r_xbot + 5*r.r_ybot;
DBPaintPlane(plane, &r, CIFPaintTable, (PaintUndoInfo *) NULL);
rc = NULL;
successes++;
}
else
{
if(trace) DumpRect("failure ",&r);
failures++;
}
}
fprintf(stderr,"END Snow Tile, size=%d failures=%d success=%d crc=%d\n",
size,
failures,
successes,
crc);
return plane;
}

View File

@ -1,77 +0,0 @@
// ************************************************************************
//
// Copyright (c) 1995-2002 Juniper Networks, Inc. All rights reserved.
//
// Permission is hereby granted, without written agreement and without
// license or royalty fees, to use, copy, modify, and distribute this
// software and its documentation for any purpose, provided that the
// above copyright notice and the following three paragraphs appear in
// all copies of this software.
//
// IN NO EVENT SHALL JUNIPER NETWORKS, INC. BE LIABLE TO ANY PARTY FOR
// DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES
// ARISING OUT OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF
// JUNIPER NETWORKS, INC. HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH
// DAMAGE.
//
// JUNIPER NETWORKS, INC. SPECIFICALLY DISCLAIMS ANY WARRANTIES,
// INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, AND
// NON-INFRINGEMENT.
//
// THE SOFTWARE PROVIDED HEREUNDER IS ON AN "AS IS" BASIS, AND JUNIPER
// NETWORKS, INC. HAS NO OBLIGATION TO PROVIDE MAINTENANCE, SUPPORT,
// UPDATES, ENHANCEMENTS, OR MODIFICATIONS.
//
// ************************************************************************
/* bpUtils.c --
*
* shared low-level routines for this module.
*
*/
#include <stdio.h>
#include "utils/utils.h"
#include "database/database.h"
#include "utils/geometry.h"
#include "bplane/bplaneInt.h"
/*
* ----------------------------------------------------------------------------
* bpRectDim --
*
* return dimension of rectangle in xDir
*
* ----------------------------------------------------------------------------
*/
int bpRectDim(Rect *r, bool xDir)
{
return xDir ? r->r_xtop - r->r_xbot : r->r_ytop - r->r_ybot;
}
/*
* ----------------------------------------------------------------------------
* bpBinIndices --
*
* compute bin indices corresponding to area.
*
* ----------------------------------------------------------------------------
*/
static __inline__ void
bpBinIndices(Rect area, /* area */
Rect binArea, /* lower left corner of bin system */
int indexBits,
int dim,
bool xDir, /* TRUE for x bin, FALSE for y bin */
int *min, /* results go here */
int *max)
{
int ref, coord;
int index;
}

View File

@ -1,235 +0,0 @@
// ************************************************************************
//
// Copyright (c) 1995-2002 Juniper Networks, Inc. All rights reserved.
//
// Permission is hereby granted, without written agreement and without
// license or royalty fees, to use, copy, modify, and distribute this
// software and its documentation for any purpose, provided that the
// above copyright notice and the following three paragraphs appear in
// all copies of this software.
//
// IN NO EVENT SHALL JUNIPER NETWORKS, INC. BE LIABLE TO ANY PARTY FOR
// DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES
// ARISING OUT OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF
// JUNIPER NETWORKS, INC. HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH
// DAMAGE.
//
// JUNIPER NETWORKS, INC. SPECIFICALLY DISCLAIMS ANY WARRANTIES,
// INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, AND
// NON-INFRINGEMENT.
//
// THE SOFTWARE PROVIDED HEREUNDER IS ON AN "AS IS" BASIS, AND JUNIPER
// NETWORKS, INC. HAS NO OBLIGATION TO PROVIDE MAINTENANCE, SUPPORT,
// UPDATES, ENHANCEMENTS, OR MODIFICATIONS.
//
// ************************************************************************
#ifndef _MAGIC__BPLANE__BPLANE_H
#define _MAGIC__BPLANE__BPLANE_H
/*
* bplane.h --
*
* This file defines the interface between the bplane
* module and the rest of max.
*
* BUGS
* ====
*
* NOTE nested enums are currently broken do to dynamic binning.
*
* OVERVIEW OF BPLANES
* ===================
*
* BPlanes ('Binned' Planes) are a data-structure for storing, sorting,
* and accessing two dimensional geometric objects.
*
* BPlanes are an alternative to Planes, i.e. corner-stitched tile planes,
* defined in the tile module.
*
* Differences between Planes and BPlanes:
* --------------------------------------
*
* 1. BPlanes are more memory efficient.
* Three pointers (+ a modest amount of binning overhead)
* replaces approximately 8 pointers (4/tile, approx. 1 space
* tile for each data tile).
*
* 2. BPlanes use a 'next' procedure for enumeration, instead of
* function call-backs. This allows client code to be simpler
* and more readable, partcularly with regard to passing state info.
* In addition gprof results are easier to interpet, since
* there is not confusion about which client procedures belong to
* a given "loop".
*
* 3. Planes fundamentally assume objects don't overlap, while BPlanes
* make no such assumption. This makes BPlanes more generally useful.
* In particular they are a natural choice for instance uses,
* labels, and non-manhattan polygons (sorted on bounding boxes).
*
* 4. Planes are optimized for merging (merging recangles
* into maximal horizontal strips) and neighbor access
* (finding nearest elements to current element). BPlanes are less
* efficient for these operations.
*
* 5. Planes generally cannot be safely modified during an enumeration,
* but BPlanes can. This makes operations such as delete, copy, and
* move simpler in BPlanes.
*
* Interface
* ---------
*
* 1. The structure of elements to be stored in BPlanes must be as
* follows:
*
* typedef struct foo
* {
* struct void *foo_bpLinks[BP_NUM_LINKS];
* Rect foo_rect;
* <client fields go here>
* } Foo
*
* 2. It is the clients responsiblity to alloc/free elements.
*
* 3. The client must set foo_rect before adding the element
* to a BPlane. foo_rect must be canonical: not inverted.
*
* 4. The BPlane module does not access or modify any client fields.
*
* 5. The client may access/modify client fields at any time.
*
* 6. As long as an element belongs to a BPlane (i.e. has been
* added via BPAdd() and not removed via BPDelete()):
*
* a. The client should not reference/modify the foo_bpLinks[] fields.
* b. The client may reference but should not modify the foo_rect
* field.
* c. The client should not call BPAdd() for the element
* (an element can only belong to one BPlane at at time).
* d. The client should not free the element!
*
* 7. The client may assume tht BP_NUM_LINKS is at least one, and
* may use foo_bpLinks[0], for his own purposes as long as an
* element does not belong to a bplane.
*
* 8. Concurrent (nested) enumerations of a bplane are permitted.
*
* 9. Elements may not be added to a bplane during active enumeration(s)
* on that bplane.
*
* 10. An element may be deleted from a bplane at any time, including
* during active enumeration(s) of that bplane. After an element
* has been deleted from a bplane, it will not be enumerated
* (i.e. returned by BPEnumNext() on that bplane).
*
* Example
* -------
*
* Here is a procedure that takes an array of id'ed rectangles and an
* area as input, and prints the ids of all rectangles impinging on the
* area.
*
* typedef struct rid
* {
* struct rid *rid_bpLinks[BP_NUM_LINKS];
* Rect rid_rect;
* char *rid_id;
* } RId;
*
* void findRects(RId data[], // ided rects
* int n, // number of rects in data
* Rect *area) // area to search
* {
* int i;
* BPEnum bpe;
* BPlane *bp;
* RId *rid;
*
* bp = BPNew();
* for(i=0;i<n;i++) BPAdd(bp,&data[i]);
*
* BPEnumInit(&bpe,bp,area,BPE_OVERLAP,"findRects");
* while(rid = BPEnumNext(&bpe))
* {
* printf("%s\n", rid->rid_id);
* }
* BPEnumTerm(&bpe);
*
*/
/* data-structures opaque to clients */
#include "bplane/bpOpaque.h"
/* create a new BPlane */
extern BPlane *BPNew(void);
/* free storate assoicated with a BPlane
* (The BPlane must be empty.)
*/
extern void BPFree(BPlane *bp);
/* add an element to a BPlane */
extern void BPAdd(BPlane *bp,
void *element);
/* remove an element from a BPlane */
extern void BPDelete(BPlane *bp,
void *element);
/* begin an enumeration */
extern void BPEnumInit(BPEnum *bpe, /* this procedure initializes this
* client supplied 'handle' for the
* enumeration.
*/
BPlane *bp, /* bplane to search */
const Rect *area, /* area to search */
int match, /* see below */
const char *id); /* for debugging */
/* match values */
/* enum all elements in the bplane (area arg must be null) */
#define BPE_ALL 0
/* element need only touch area */
#define BPE_TOUCH 1
/* some part of element must be inside (not just on boundary of) area */
#define BPE_OVERLAP 2
/* elements rect must be identical to area */
#define BPE_EQUAL 3
/* return next element in enumeration (returns NULL if none) */
#include "bplane/bpEnum.h"
/* inlined extern void *BPEnumNext(BPEnum *bpe); */
/* terminate enumeration
*
* (unterminated enumerations can cause great inefficiency since
* all active enumerations for a bplane must be considered whenever
* an element is added or deleted.)
*/
extern void BPEnumTerm(BPEnum *bpe);
/* get current bounding box of BPlane */
extern Rect BPBBox(BPlane *bp);
/* compute number of bytes used by BPlane
* (does not count memory of the elements themselves)
*/
extern unsigned int BPStatMemory(BPlane *bp);
/* tabulate statistics on a bplane */
extern unsigned int
BPStat(BPlane *bp,
int *totCount, /* ret total number of elements */
int *inBox, /* ret num of elements in inBox */
int *totBins, /* ret tot num of bins */
int *emptyBins, /* ret num of empty bins */
int *binArraysp, /* ret num of bin arrays */
int *maxEffp, /* ret max effective list length */
int *maxBinCount, /* ret max count for regular bin */
int *totUnbinned, /* ret tot num of e's not binned */
int *maxDepth); /* ret max bin array depth */
#endif /* _MAGIC__BPLANE__BPLANE_H */

View File

@ -1,82 +0,0 @@
// ************************************************************************
//
// Copyright (c) 1995-2002 Juniper Networks, Inc. All rights reserved.
//
// Permission is hereby granted, without written agreement and without
// license or royalty fees, to use, copy, modify, and distribute this
// software and its documentation for any purpose, provided that the
// above copyright notice and the following three paragraphs appear in
// all copies of this software.
//
// IN NO EVENT SHALL JUNIPER NETWORKS, INC. BE LIABLE TO ANY PARTY FOR
// DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES
// ARISING OUT OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF
// JUNIPER NETWORKS, INC. HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH
// DAMAGE.
//
// JUNIPER NETWORKS, INC. SPECIFICALLY DISCLAIMS ANY WARRANTIES,
// INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, AND
// NON-INFRINGEMENT.
//
// THE SOFTWARE PROVIDED HEREUNDER IS ON AN "AS IS" BASIS, AND JUNIPER
// NETWORKS, INC. HAS NO OBLIGATION TO PROVIDE MAINTENANCE, SUPPORT,
// UPDATES, ENHANCEMENTS, OR MODIFICATIONS.
//
// ************************************************************************
/*
* bplaneInt.h --
*
* This file defines constants and datastructures used internally by the
* bplane module, but not exported to the rest of the world.
*/
#ifndef _MAGIC__BPLANE__BPLANEINT_H
#define _MAGIC__BPLANE__BPLANEINT_H
/* Tcl linked Parameters */
extern int bpMinBAPop; /* don't sub(bin) when count less than this
*/
extern double bpMinAvgBinPop; /* try to keep average bin pop at or
* below this
*/
/* LabeledElement
*
* Used in this module as elements for test bplanes.
*/
typedef struct labeledelement
{
struct element *le_links[BP_NUM_LINKS];
Rect le_rect;
/* client data goes here */
char * le_text;
} LabeledElement;
/* bins */
extern void bpBinsUpdate(BPlane *bp);
extern void bpBinAdd(BinArray *ba, Element *e);
extern BinArray *bpBinArrayBuild(Rect bbox,
Element *elements, /* initial elements */
bool subbin); /* subbin as needed */
/* dump (for debug) */
extern void bpDumpRect(Rect *r);
extern void bpDump(BPlane *bp, int flags);
/* bpDump flags */
/* labeled elements */
# define BPD_LABELED 1
# define BPD_INTERNAL_UNITS 2
/* test */
void bpTestSnowGold(int size, bool trace);
extern BPlane *bpTestSnow(int size, bool trace);
extern Plane *bpTestSnowTile(int size, bool trace);
extern int bpRand(int min, int max);
#endif /* _MAGIC__BPLANE__BPLANEINT_H */

File diff suppressed because it is too large Load Diff

View File

@ -4,26 +4,25 @@
* Input of Calma GDS-II stream format.
* Low-level input.
*
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
*/
#ifndef lint
static const char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magic-8.0/calma/CalmaRdio.c,v 1.1.1.1 2008/02/03 20:43:50 tim Exp $";
static char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magic-8.0/calma/CalmaRdio.c,v 1.1.1.1 2008/02/03 20:43:50 tim Exp $";
#endif /* not lint */
#include <stdio.h>
#include <sys/types.h>
#include <time.h>
#include <netinet/in.h>
@ -46,14 +45,11 @@ static const char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magi
#include "textio/textio.h"
#include "calma/calmaInt.h"
/* C99 compat */
#include "calma/calma.h"
/* Forward declarations */
bool calmaReadR8(double *pd);
bool calmaSkipBytes(int nbytes);
bool calmaReadR8();
bool calmaSkipBytes();
/*
* ----------------------------------------------------------------------------
*
@ -73,9 +69,9 @@ bool calmaSkipBytes(int nbytes);
*/
bool
calmaReadTransform(
Transform *ptrans, /* Fill in this transform */
char *name) /* Name of subcell (for errors) */
calmaReadTransform(ptrans, name)
Transform *ptrans; /* Fill in this transform */
char *name; /* Name of subcell (for errors) */
{
int nbytes, rtype, flags, angle;
double dangle;
@ -114,8 +110,8 @@ calmaReadTransform(
if (dmag != (double)((int)(dmag + 0.5)))
{
CalmaReadError("Non-integer magnification (%g) in transform\n", dmag);
CalmaReadError("Rounding to %d.\n", (int)(dmag + 0.5));
calmaReadError("Non-integer magnification (%g) in transform\n", dmag);
calmaReadError("Rounding to %d.\n", (int)(dmag + 0.5));
}
GeoScaleTrans(ptrans, (int)(dmag + 0.5), &t);
*ptrans = t;
@ -148,13 +144,13 @@ calmaReadTransform(
case 0: case 90: case 180: case 270:
break;
default:
CalmaReadError("Non-Manhattan angle (%d) in transform\n", angle);
calmaReadError("Non-Manhattan angle (%d) in transform\n", angle);
if (angle < 45) angle = 0;
else if (angle < 135) angle = 90;
else if (angle < 225) angle = 180;
else if (angle < 315) angle = 270;
else angle = 0;
CalmaReadError(" Rounding to %d degrees.\n", angle);
calmaReadError(" Rounding to %d degrees.\n", angle);
}
/*
@ -184,7 +180,7 @@ calmaReadTransform(
return (TRUE);
}
/*
* ----------------------------------------------------------------------------
*
@ -205,9 +201,9 @@ calmaReadTransform(
*/
bool
calmaReadI2Record(
int type, /* Type of record expected */
int *pvalue) /* Store value here */
calmaReadI2Record(type, pvalue)
int type; /* Type of record expected */
int *pvalue; /* Store value here */
{
int nbytes, rtype, n;
@ -222,15 +218,15 @@ calmaReadI2Record(
/* Read the value */
READI2(n);
if (FEOF(calmaInputFile)) goto eof;
if (feof(calmaInputFile)) goto eof;
*pvalue = n;
return (TRUE);
eof:
CalmaReadError("Unexpected EOF.\n");
calmaReadError("Unexpected EOF.\n");
return (FALSE);
}
/*
* ----------------------------------------------------------------------------
*
@ -250,9 +246,9 @@ eof:
*/
bool
calmaReadI4Record(
int type, /* Type of record expected */
int *pvalue) /* Store value here */
calmaReadI4Record(type, pvalue)
int type; /* Type of record expected */
int *pvalue; /* Store value here */
{
int nbytes, rtype, n;
@ -267,90 +263,15 @@ calmaReadI4Record(
/* Read the value */
READI4(n);
if (FEOF(calmaInputFile)) goto eof;
if (feof(calmaInputFile)) goto eof;
*pvalue = n;
return (TRUE);
eof:
CalmaReadError("Unexpected EOF.\n");
calmaReadError("Unexpected EOF.\n");
return (FALSE);
}
/*
* ----------------------------------------------------------------------------
*
* calmaReadStampRecord --
*
* Read a record that contains a pair of timestamps for creation and
* modification dates.
*
* Results:
* TRUE on success, FALSE if the record type we read is not
* what we're expecting.
*
* Side effects:
* Consumes input.
* Translates the creation timestamp from GDS format to a standard
* UNIX (time.h) timestamp (seconds since the epoch).
* Stores the result in the integer pointed to by 'stampptr'.
*
* ----------------------------------------------------------------------------
*/
bool
calmaReadStampRecord(
int type,
int *stampptr)
{
int nbytes, rtype;
struct tm gds_timestamp;
READRH(nbytes, rtype);
if (nbytes < 0)
goto eof;
if (type != rtype)
{
calmaUnexpected(type, rtype);
return (FALSE);
}
nbytes -= CALMAHEADERLENGTH;
if (nbytes != 24)
{
/* Not dealing with any timestamp that is not in I2 format */
calmaSkipBytes(nbytes);
if (stampptr) *stampptr = 0;
CalmaReadError("Unknown timestamp format; setting timestamp to zero.\n");
return TRUE;
}
gds_timestamp.tm_wday = 0; /* Not used by mktime() */
gds_timestamp.tm_yday = 0; /* Not used by mktime() */
gds_timestamp.tm_isdst = -1;
READI2(gds_timestamp.tm_year);
READI2(gds_timestamp.tm_mon);
READI2(gds_timestamp.tm_mday);
READI2(gds_timestamp.tm_hour);
READI2(gds_timestamp.tm_min);
READI2(gds_timestamp.tm_sec);
/* GDS timestamps differ from UNIX time structure only by a */
/* difference of 1 in the month count. */
gds_timestamp.tm_mon--;
/* Skip the modification date timestamp */
(void) calmaSkipBytes(nbytes - 12);
if (stampptr) *stampptr = (int)mktime(&gds_timestamp);
return (TRUE);
eof:
CalmaReadError("Unexpected EOF.\n");
return (FALSE);
}
/*
* ----------------------------------------------------------------------------
*
@ -371,9 +292,9 @@ eof:
*/
bool
calmaReadStringRecord(
int type,
char **str)
calmaReadStringRecord(type, str)
int type;
char **str;
{
int nbytes, rtype;
@ -389,17 +310,17 @@ calmaReadStringRecord(
nbytes -= CALMAHEADERLENGTH;
*str = (char *) mallocMagic(nbytes + 1);
if (magicFREAD(*str, sizeof (char), nbytes, calmaInputFile) != nbytes)
if (fread(*str, sizeof (char), nbytes, calmaInputFile) != nbytes)
goto eof;
*(*str + nbytes) = '\0';
return (TRUE);
eof:
CalmaReadError("Unexpected EOF.\n");
calmaReadError("Unexpected EOF.\n");
return (FALSE);
}
/*
* ----------------------------------------------------------------------------
*
@ -420,21 +341,21 @@ eof:
*/
bool
calmaReadR8(
double *pd) /* Store result in *pd */
calmaReadR8(pd)
double *pd; /* Store result in *pd */
{
int i, exponent;
unsigned char dchars[8];
double mantissa, d;
bool isneg;
if (magicFREAD((char *) dchars, sizeof (char), sizeof dchars,
if (fread((char *) dchars, sizeof (char), sizeof dchars,
calmaInputFile) != sizeof dchars)
return (FALSE);
/* Extract the sign and exponent */
exponent = dchars[0];
if ((isneg = (exponent & 0x80)))
if (isneg = (exponent & 0x80))
exponent &= ~0x80;
exponent -= 64;
@ -466,7 +387,7 @@ calmaReadR8(
*pd = d;
return (TRUE);
}
/*
* ----------------------------------------------------------------------------
*
@ -489,10 +410,10 @@ calmaReadR8(
*/
void
calmaSkipSet(
const int *skipwhat)
calmaSkipSet(skipwhat)
int *skipwhat;
{
const int *skipp;
int *skipp;
int nbytes, rtype;
for (;;)
@ -512,7 +433,7 @@ skipit:
(void) calmaSkipBytes(nbytes - CALMAHEADERLENGTH);
}
}
/*
* ----------------------------------------------------------------------------
*
@ -533,8 +454,8 @@ skipit:
*/
bool
calmaSkipExact(
int type)
calmaSkipExact(type)
int type;
{
int nbytes, rtype;
@ -557,10 +478,10 @@ calmaSkipExact(
return (TRUE);
eof:
CalmaReadError("Unexpected EOF.\n");
calmaReadError("Unexpected EOF.\n");
return (FALSE);
}
/*
* ----------------------------------------------------------------------------
*
@ -579,8 +500,8 @@ eof:
*/
bool
calmaSkipTo(
int what)
calmaSkipTo(what)
int what;
{
int nbytes, rtype;
@ -594,7 +515,7 @@ calmaSkipTo(
return (TRUE);
}
/*
* ----------------------------------------------------------------------------
*
@ -615,11 +536,11 @@ calmaSkipTo(
*/
bool
calmaSkipBytes(
int nbytes) /* Skip this many bytes */
calmaSkipBytes(nbytes)
int nbytes; /* Skip this many bytes */
{
while (nbytes-- > 0)
if (FGETC(calmaInputFile) < 0)
if (getc(calmaInputFile) < 0)
return (FALSE);
return (TRUE);

View File

@ -4,21 +4,21 @@
* Input of Calma GDS-II stream format.
* Processing of paint (paths, boxes, and boundaries) and text.
*
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
*/
#ifndef lint
static const char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magic-8.0/calma/CalmaRdpt.c,v 1.7 2010/08/25 17:33:54 tim Exp $";
static char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magic-8.0/calma/CalmaRdpt.c,v 1.7 2010/08/25 17:33:54 tim Exp $";
#endif /* not lint */
#include <stdio.h>
@ -48,17 +48,16 @@ static const char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magi
#include "calma/calmaInt.h"
#include "calma/calma.h"
/* C99 compat */
#include "drc/drc.h"
extern int calmaNonManhattan;
extern int CalmaPolygonCount;
extern int CalmaPathCount;
extern HashTable calmaDefInitHash;
extern void calmaLayerError(char *mesg, int layer, int dt);
CIFPath *calmaReadPath(int iscale);
extern void calmaLayerError();
bool calmaReadPath();
typedef enum { LABEL_TYPE_NONE, LABEL_TYPE_TEXT, LABEL_TYPE_PORT } labelType;
/*
* ----------------------------------------------------------------------------
@ -82,9 +81,8 @@ CIFPath *calmaReadPath(int iscale);
*/
void
calmaInputRescale(
int n,
int d)
calmaInputRescale(n, d)
int n, d;
{
HashEntry *h;
HashSearch hs;
@ -102,9 +100,7 @@ calmaInputRescale(
{
/* Scale the GDS planes in this cell's cd_client record */
Plane **gdsplanes = (Plane **)def->cd_client;
/* Should not happen, but punt if client record is not set; */
if (def->cd_client != (ClientData)0)
CIFScalePlanes(n, d, gdsplanes);
CIFScalePlanes(n, d, gdsplanes);
}
}
@ -136,9 +132,9 @@ calmaInputRescale(
*/
void
calmaReadPoint(
Point *p,
int iscale)
calmaReadPoint(p, iscale)
Point *p;
int iscale;
{
int rescale;
@ -149,7 +145,7 @@ calmaReadPoint(
rescale = calmaReadScale2 / FindGCF(calmaReadScale2, abs(p->p_x));
if ((calmaReadScale1 * rescale) > CIFRescaleLimit)
{
CalmaReadError("Warning: calma units at max scale; value rounded\n");
calmaReadError("Warning: calma units at max scale; value rounded\n");
if (p->p_x < 0)
p->p_x -= ((calmaReadScale2 - 1) >> 1);
else
@ -171,7 +167,7 @@ calmaReadPoint(
rescale = calmaReadScale2 / FindGCF(calmaReadScale2, abs(p->p_y));
if ((calmaReadScale1 * rescale) > CIFRescaleLimit)
{
CalmaReadError("Warning: calma units at max scale; value rounded\n");
calmaReadError("Warning: calma units at max scale; value rounded\n");
if (p->p_y < 0)
p->p_y -= ((calmaReadScale2 - 1) >> 1);
else
@ -188,7 +184,7 @@ calmaReadPoint(
p->p_y /= calmaReadScale2;
}
/*
* ----------------------------------------------------------------------------
*
@ -206,14 +202,14 @@ calmaReadPoint(
*/
void
calmaElementBoundary(void)
calmaElementBoundary()
{
int dt, layer, ciftype;
CIFPath *pathheadp;
LinkedRect *rp;
Plane *plane;
CellUse *use;
CellDef *savedef = NULL, *newdef = NULL;
CellDef *savedef, *newdef = NULL;
/* Skip CALMA_ELFLAGS, CALMA_PLEX */
calmaSkipSet(calmaElementIgnore);
@ -222,7 +218,7 @@ calmaElementBoundary(void)
if (!calmaReadI2Record(CALMA_LAYER, &layer)
|| !calmaReadI2Record(CALMA_DATATYPE, &dt))
{
CalmaReadError("Missing layer or datatype in boundary/box.\n");
calmaReadError("Missing layer or datatype in boundary/box.\n");
return;
}
@ -237,11 +233,10 @@ calmaElementBoundary(void)
plane = cifCurReadPlanes[ciftype];
/* Read the path itself, building up a path structure */
pathheadp = calmaReadPath((plane == NULL) ? 0 : 1);
if (pathheadp == NULL)
if (!calmaReadPath(&pathheadp, (plane == NULL) ? 0 : 1))
{
if (plane != NULL)
CalmaReadError("Error while reading path for boundary/box; ignored.\n");
calmaReadError("Error while reading path for boundary/box; ignored.\n");
return;
}
@ -249,27 +244,23 @@ calmaElementBoundary(void)
/* so we need to set it again. */
if (ciftype >= 0) plane = cifCurReadPlanes[ciftype];
/* Save non-Manhattan polygons in their own subcells. */
/* NOTE: CALMA_POLYGON_TEMP and CALMA_POLYGON_KEEP read in polygons much
* faster, but that interferes with boolean processing. This method
* needs to be reworked.
*/
/* Convert the polygon to rectangles. */
if ((CalmaSubcellPolygons != CALMA_POLYGON_NONE) && (calmaNonManhattan > 0))
if (CalmaSubcellPolygons && (calmaNonManhattan > 0))
{
/* Place the polygon in its own subcell */
char newname[20];
char newname[] = "polygonXXXXX";
HashEntry *he;
savedef = cifReadCellDef;
/* Make up name for cell */
snprintf(newname, sizeof(newname), "polygon%05d", ++CalmaPolygonCount);
sprintf(newname + 7, "%05d", ++CalmaPolygonCount);
he = HashFind(&calmaDefInitHash, newname);
if (!HashGetValue(he))
{
newdef = calmaFindCell(newname, NULL, NULL);
newdef = calmaFindCell(newname, NULL);
cifReadCellDef = newdef;
DBCellClearDef(cifReadCellDef);
DBCellSetAvail(cifReadCellDef);
@ -283,9 +274,8 @@ calmaElementBoundary(void)
}
}
/* Convert the polygon to rectangles. */
rp = CIFPolyToRects(pathheadp, plane, CIFPaintTable, (PaintUndoInfo *)NULL, TRUE);
CIFPropRecordPath(cifReadCellDef, pathheadp, FALSE);
rp = CIFPolyToRects(pathheadp, plane, CIFPaintTable, (PaintUndoInfo *)NULL);
CIFFreePath(pathheadp);
/* If the input layer is designated for ports by a "label" */
@ -299,18 +289,8 @@ calmaElementBoundary(void)
if (rp != NULL)
{
Rect rpc;
int savescale;
/* Convert rp to magic database units to compare to label rects */
rpc = rp->r_r;
rpc.r_xbot /= cifCurReadStyle->crs_scaleFactor;
rpc.r_xtop /= cifCurReadStyle->crs_scaleFactor;
rpc.r_ybot /= cifCurReadStyle->crs_scaleFactor;
rpc.r_ytop /= cifCurReadStyle->crs_scaleFactor;
if ((ciftype >= 0) &&
(cifCurReadStyle->crs_labelSticky[ciftype] != LABEL_TYPE_NONE))
((cifCurReadStyle->crs_labelSticky[ciftype] != LABEL_TYPE_NONE)))
{
Label *lab;
TileType type;
@ -318,60 +298,26 @@ calmaElementBoundary(void)
type = cifCurReadStyle->crs_labelLayer[ciftype];
for (lab = cifReadCellDef->cd_labels; lab; lab = lab->lab_next)
{
if ((GEO_SURROUND(&rpc, &lab->lab_rect)) && (lab->lab_type == type))
if ((GEO_SURROUND(&rp->r_r, &lab->lab_rect)) && (lab->lab_type == type))
{
lab->lab_rect = rpc; /* Replace with larger rectangle */
lab->lab_rect = rp->r_r; /* Replace with larger rectangle */
break;
}
}
if (lab == NULL)
{
/* There was no label in the area. Create a placeholder label */
lab = DBPutLabel(cifReadCellDef, &rpc, GEO_CENTER, "", type, 0, 0);
}
if ((cifCurReadStyle->crs_labelSticky[ciftype] == LABEL_TYPE_PORT)
&& ((lab->lab_flags & PORT_DIR_MASK) == 0))
{
/* Label was read previously as a text type, but the pin layer
* causes it to be recast as a port, or corresponding label has
* not yet been seen.
*/
int i, idx;
Label *sl;
/* Order ports as encountered. */
i = -1;
for (sl = cifReadCellDef->cd_labels; sl != NULL; sl = sl->lab_next)
{
idx = sl->lab_port;
if (idx > i) i = idx;
if ((idx > 0) && (sl != lab) && !strcmp(sl->lab_text, lab->lab_text))
{
i = idx - 1;
break;
}
}
i++;
lab->lab_port = i;
lab->lab_flags |= PORT_DIR_NORTH | PORT_DIR_SOUTH |
PORT_DIR_EAST | PORT_DIR_WEST;
}
}
}
/* Paint the rectangles (if any) */
free_magic1_t mm1 = freeMagic1_init();
for (; rp != NULL ; rp = rp->r_next)
{
if (plane)
DBPaintPlane(plane, &rp->r_r, CIFPaintTable, (PaintUndoInfo *)NULL);
freeMagic1(&mm1, (char *) rp);
freeMagic((char *) rp);
}
freeMagic1_end(&mm1);
if (cifCurReadPlanes == cifEditCellPlanes)
{
CIFPaintCurrent(FILE_CALMA);
CIFPaintCurrent();
DBReComputeBbox(cifReadCellDef);
DRCCheckThis(cifReadCellDef, TT_CHECKPAINT, &cifReadCellDef->cd_bbox);
DBWAreaChanged(cifReadCellDef, &cifReadCellDef->cd_bbox,
@ -387,7 +333,7 @@ calmaElementBoundary(void)
DBPlaceCell(use, cifReadCellDef);
}
}
/*
* ----------------------------------------------------------------------------
*
@ -410,7 +356,7 @@ calmaElementBoundary(void)
*/
void
calmaElementBox(void)
calmaElementBox()
{
int nbytes, rtype, npoints, savescale;
int dt, layer, ciftype;
@ -425,7 +371,7 @@ calmaElementBox(void)
if (!calmaReadI2Record(CALMA_LAYER, &layer)
|| !calmaReadI2Record(CALMA_BOXTYPE, &dt))
{
CalmaReadError("Missing layer or datatype in boundary/box.\n");
calmaReadError("Missing layer or datatype in boundary/box.\n");
return;
}
@ -449,7 +395,7 @@ calmaElementBox(void)
READRH(nbytes, rtype);
if (nbytes < 0)
{
CalmaReadError("EOF when reading box.\n");
calmaReadError("EOF when reading box.\n");
return;
}
if (rtype != CALMA_XY)
@ -462,7 +408,7 @@ calmaElementBox(void)
npoints = (nbytes - CALMAHEADERLENGTH) / 8;
if (npoints != 5)
{
CalmaReadError("Box doesn't have 5 points.\n");
calmaReadError("Box doesn't have 5 points.\n");
(void) calmaSkipBytes(nbytes - CALMAHEADERLENGTH);
return;
}
@ -505,9 +451,9 @@ calmaElementBox(void)
*/
void
calmaElementPath(void)
calmaElementPath()
{
int nbytes = -1, rtype = 0, extend1, extend2;
int nbytes, rtype, extend1, extend2;
int layer, dt, width, pathtype, ciftype, savescale;
int xmin, ymin, xmax, ymax, temp;
CIFPath *pathheadp, *pathp, *previousp;
@ -515,7 +461,7 @@ calmaElementPath(void)
Plane *plane;
int first,last;
CellUse *use;
CellDef *savedef = NULL, *newdef = NULL;
CellDef *savedef, *newdef = NULL;
/* Skip CALMA_ELFLAGS, CALMA_PLEX */
calmaSkipSet(calmaElementIgnore);
@ -533,7 +479,7 @@ calmaElementPath(void)
if (pathtype != CALMAPATH_SQUAREFLUSH && pathtype != CALMAPATH_SQUAREPLUS &&
pathtype != CALMAPATH_CUSTOM)
{
CalmaReadError("Warning: pathtype %d unsupported (ignored).\n", pathtype);
calmaReadError("Warning: pathtype %d unsupported (ignored).\n", pathtype);
pathtype = CALMAPATH_SQUAREFLUSH;
}
@ -542,18 +488,18 @@ calmaElementPath(void)
* Allow zero-width paths; we will ignore them later.
*/
width = 0;
PEEKRH(nbytes, rtype)
PEEKRH(nbytes, rtype)
if (nbytes > 0 && rtype == CALMA_WIDTH)
{
if (!calmaReadI4Record(CALMA_WIDTH, &width))
if (!calmaReadI4Record(CALMA_WIDTH, &width))
{
CalmaReadError("Error in reading WIDTH in calmaElementPath()\n") ;
calmaReadError("Error in reading WIDTH in calmaElementPath()\n") ;
return;
}
}
width *= calmaReadScale1;
if (width % calmaReadScale2 != 0)
CalmaReadError("Wire width snapped to nearest integer boundary.\n");
calmaReadError("Wire width snapped to nearest integer boundary.\n");
width /= calmaReadScale2;
@ -570,12 +516,12 @@ calmaElementPath(void)
if (nbytes > 0 && rtype == CALMA_BGNEXTN)
{
if (!calmaReadI4Record(CALMA_BGNEXTN, &extend1))
CalmaReadError("Error in reading BGNEXTN in path (ignored)\n") ;
calmaReadError("Error in reading BGNEXTN in path (ignored)\n") ;
else
{
extend1 *= calmaReadScale1;
if (extend1 % calmaReadScale2 != 0)
CalmaReadError("Wire extension snapped to nearest integer boundary.\n");
calmaReadError("Wire extension snapped to nearest integer boundary.\n");
extend1 *= 2;
extend1 /= calmaReadScale2;
}
@ -585,12 +531,12 @@ calmaElementPath(void)
if (nbytes > 0 && rtype == CALMA_ENDEXTN)
{
if (!calmaReadI4Record(CALMA_ENDEXTN, &extend2))
CalmaReadError("Error in reading ENDEXTN in path (ignored)\n") ;
calmaReadError("Error in reading ENDEXTN in path (ignored)\n") ;
else
{
extend2 *= calmaReadScale1;
if (extend2 % calmaReadScale2 != 0)
CalmaReadError("Wire extension snapped to nearest integer boundary.\n");
calmaReadError("Wire extension snapped to nearest integer boundary.\n");
extend2 *= 2;
extend2 /= calmaReadScale2;
}
@ -598,10 +544,9 @@ calmaElementPath(void)
/* Read the points in the path */
savescale = calmaReadScale1;
pathheadp = calmaReadPath(2);
if (pathheadp == NULL)
if (!calmaReadPath(&pathheadp, 2))
{
CalmaReadError("Improper path; ignored.\n");
calmaReadError("Improper path; ignored.\n");
return;
}
if (savescale != calmaReadScale1)
@ -667,18 +612,18 @@ calmaElementPath(void)
if (CalmaSubcellPaths)
{
/* Place the path in its own subcell */
char newname[16];
char newname[] = "pathXXXXX";
HashEntry *he;
savedef = cifReadCellDef;
/* Make up name for cell */
snprintf(newname, sizeof(newname), "path%05d", ++CalmaPathCount);
sprintf(newname + 4, "%05d", ++CalmaPathCount);
he = HashFind(&calmaDefInitHash, newname);
if (!HashGetValue(he))
{
newdef = calmaFindCell(newname, NULL, NULL);
newdef = calmaFindCell(newname, NULL);
cifReadCellDef = newdef;
DBCellClearDef(cifReadCellDef);
DBCellSetAvail(cifReadCellDef);
@ -692,14 +637,14 @@ calmaElementPath(void)
}
}
CIFPropRecordPath(cifReadCellDef, pathheadp, TRUE, "path");
CIFPropRecordPath(cifReadCellDef, pathheadp, TRUE);
CIFPaintWirePath(pathheadp, width,
(pathtype == CALMAPATH_SQUAREFLUSH || pathtype == CALMAPATH_CUSTOM) ?
FALSE : TRUE, plane, CIFPaintTable, (PaintUndoInfo *)NULL);
if (cifCurReadPlanes == cifEditCellPlanes)
{
CIFPaintCurrent(FILE_CALMA);
CIFPaintCurrent();
DBReComputeBbox(cifReadCellDef);
DRCCheckThis(cifReadCellDef, TT_CHECKPAINT, &cifReadCellDef->cd_bbox);
DBWAreaChanged(cifReadCellDef, &cifReadCellDef->cd_bbox,
@ -734,16 +679,17 @@ calmaElementPath(void)
*/
void
calmaElementText(void)
calmaElementText()
{
static const int ignore[] = { CALMA_PATHTYPE, CALMA_WIDTH, -1 };
static int ignore[] = { CALMA_PATHTYPE, CALMA_WIDTH, -1 };
char *textbody = NULL;
int nbytes = -1, rtype = 0;
int layer, textt, cifnum, textpres;
int nbytes, rtype;
int layer, textt, cifnum;
TileType type;
Rect r;
unsigned short textpres;
double dval;
int size, micron, angle, font, pos, portnum, idx;
int size, angle, font, pos;
/* Skip CALMA_ELFLAGS, CALMA_PLEX */
calmaSkipSet(calmaElementIgnore);
@ -754,7 +700,7 @@ calmaElementText(void)
cifnum = CIFCalmaLayerToCifLayer(layer, textt, cifCurReadStyle);
if (cifnum < 0)
{
if (cifCurReadStyle->crs_flags & CRF_IGNORE_UNKNOWNLAYER_LABELS)
if(cifCurReadStyle->crs_flags & CRF_IGNORE_UNKNOWNLAYER_LABELS)
type = -1;
else {
calmaLayerError("Label on unknown layer/datatype", layer, textt);
@ -765,29 +711,10 @@ calmaElementText(void)
font = -1;
angle = 0;
portnum = 0;
/* Use the minimum width of the layer on which the text is placed
* as the default text size, or 1um, whichever is smaller. Account
* for the 8/10 difference encoded in the rendered font height.
*/
size = 0;
if (type > 0)
{
size = DRCGetDefaultLayerWidth(type);
if (size > 0)
{
size *= (calmaReadScale2 * cifCurReadStyle->crs_multiplier * 8);
size /= (calmaReadScale1 * cifCurReadStyle->crs_scaleFactor * 10);
}
}
/* Default or maximum size is 1um */
micron = (int)((800 * cifCurReadStyle->crs_multiplier)
/* Default size is 1um */
size = (int)((800 * cifCurReadStyle->crs_multiplier)
/ cifCurReadStyle->crs_scaleFactor);
if ((size == 0) || (size > micron))
size = micron;
/* Default position is bottom-right (but what the spec calls "top-left"!) */
pos = GEO_SOUTHEAST;
@ -833,31 +760,6 @@ calmaElementText(void)
else if (nbytes > 0 && rtype != CALMA_STRANS)
calmaSkipSet(ignore);
/* NOTE: Record may contain both PRESENTATION and WIDTH */
PEEKRH(nbytes, rtype);
if (nbytes > 0 && rtype == CALMA_WIDTH)
{
int width;
/* Use WIDTH value to set the font size */
if (!calmaReadI4Record(CALMA_WIDTH, &width))
{
CalmaReadError("Error in reading WIDTH in calmaElementText()\n") ;
return;
}
width *= calmaReadScale1;
if (width % calmaReadScale2 != 0)
CalmaReadError("Text width snapped to nearest integer boundary.\n");
width /= calmaReadScale2;
/* Convert to database units, because dimension goes to PutLabel */
/* and is not converted through CIFPaintCurrent(). */
size = CIFScaleCoord(width, COORD_ANY);
}
else if (nbytes > 0 && rtype != CALMA_STRANS)
calmaSkipSet(ignore);
READRH(nbytes, rtype);
if (nbytes > 0 && rtype == CALMA_STRANS)
{
@ -868,20 +770,10 @@ calmaElementText(void)
if (nbytes > 0 && rtype == CALMA_MAG)
{
calmaReadR8(&dval);
/* Sanity check on dval (must be nonzero positive) */
if ((dval <= 0) || (dval > 10000))
{
CalmaReadError("Invalid text magnification %lg.\n", dval);
/* Keep default size */
}
else
/* Assume that MAG is the label size in microns */
/* "size" is the label size in 10 * (database units) */
/* The "calma magscale" option can be used to */
/* reinterpret the size for any specific GDS file. */
size = (int)(0.5 + ((dval * 1000 * CalmaMagScale
* cifCurReadStyle->crs_multiplier)
/ cifCurReadStyle->crs_scaleFactor));
/* Assume that MAG is the label size in microns */
/* "size" is the label size in 8 * (database units) */
size = (int)((dval * 800 * cifCurReadStyle->crs_multiplier)
/ cifCurReadStyle->crs_scaleFactor);
}
else
UNREADRH(nbytes, rtype);
@ -910,7 +802,7 @@ calmaElementText(void)
nbytes -= CALMAHEADERLENGTH;
if (nbytes < 8)
{
CalmaReadError("Not enough bytes in point record.\n");
calmaReadError("Not enough bytes in point record.\n");
}
else
{
@ -933,7 +825,7 @@ calmaElementText(void)
* a flag for that in the "cifoutput" section of the techfile.
*/
#if 0
#if 0
{
static bool algmsg = FALSE;
@ -942,7 +834,7 @@ calmaElementText(void)
char *savstring;
for (cp = textbody; *cp; cp++)
{
if (*cp <= ' ' | *cp > '~')
if (*cp <= ' ' | *cp > '~')
{
if (!changed)
{
@ -951,7 +843,7 @@ calmaElementText(void)
}
if (*cp == '\r' && *(cp+1) == '\0')
*cp = '\0';
else if (*cp == '\r')
else if (*cp == '\r')
*cp = '_';
else if (*cp == ' ')
*cp = '_';
@ -960,15 +852,15 @@ calmaElementText(void)
}
}
if (changed) {
CalmaReadError("Warning: improper characters fixed in label '%s'\n",
calmaReadError("Warning: improper characters fixed in label '%s'\n",
savstring);
if (!algmsg) {
algmsg = TRUE;
CalmaReadError(" (algorithm used: trailing <CR> dropped, "
calmaReadError(" (algorithm used: trailing <CR> dropped, "
"<CR> and ' ' changed to '_', \n"
" other non-printables changed to '?')\n");
}
CalmaReadError(" modified label is '%s'\n", textbody);
calmaReadError(" modified label is '%s'\n", textbody);
freeMagic(savstring);
}
}
@ -978,110 +870,53 @@ calmaElementText(void)
/* Place the label */
if (strlen(textbody) == 0)
{
CalmaReadError("Warning: Ignoring empty string label at (%d, %d)\n",
calmaReadError("Warning: Ignoring empty string label at (%d, %d)\n",
r.r_ll.p_x * cifCurReadStyle->crs_scaleFactor,
r.r_ll.p_y * cifCurReadStyle->crs_scaleFactor);
}
else if (cifCurReadStyle->crs_labelSticky[cifnum] == LABEL_TYPE_CELLID)
{
/* Special handling of label layers marked "cellid" in the techfile. */
/* The actual cellname is the ID string, not the GDS structure name. */
DBCellRenameDef(cifReadCellDef, textbody);
}
else if (type < 0)
{
if (!(cifCurReadStyle->crs_flags & CRF_IGNORE_UNKNOWNLAYER_LABELS))
CalmaReadError("Warning: label \"%s\" at (%d, %d) is on unhandled"
" layer:purpose pair %d:%d and will be discarded.\n", textbody,
r.r_ll.p_x * cifCurReadStyle->crs_scaleFactor,
r.r_ll.p_y * cifCurReadStyle->crs_scaleFactor, layer, textt);
calmaReadError("Warning: label \"%s\" at (%d, %d) is on unhandled"
" layer:purpose pair %d:%d and will be discarded.\n", textbody,
r.r_ll.p_x * cifCurReadStyle->crs_scaleFactor,
r.r_ll.p_y * cifCurReadStyle->crs_scaleFactor, layer, textt);
}
else
{
int flags, i;
Label *lab;
Label *sl;
if (type == TT_SPACE)
/* Assigning GDS layer to space prevents making the label sticky */
flags = 0;
else if (cifnum >= 0 && (cifCurReadStyle->crs_labelSticky[cifnum] != LABEL_TYPE_NONE))
if (cifnum >= 0 && (cifCurReadStyle->crs_labelSticky[cifnum] != LABEL_TYPE_NONE))
flags = LABEL_STICKY;
else if (cifCurReadStyle->crs_flags & CRF_NO_RECONNECT_LABELS)
flags = LABEL_STICKY;
else
flags = 0;
/* If there is an empty-string label surrounding the label position */
/* then replace the position with the larger one and remove the */
/* empty label. */
sl = NULL;
for (lab = cifReadCellDef->cd_labels; lab != NULL; lab = lab->lab_next)
{
if (lab->lab_text[0] == '\0')
{
if ((GEO_SURROUND(&lab->lab_rect, &r)) && (lab->lab_type == type))
{
r = lab->lab_rect;
if (sl == NULL)
cifReadCellDef->cd_labels = lab->lab_next;
else
sl->lab_next = lab->lab_next;
if (cifReadCellDef->cd_lastLabel == lab)
cifReadCellDef->cd_lastLabel = sl;
/* Port number from the placeholder is ignored; find
* a new valid port number for the new label name.
*/
i = -1;
for (sl = cifReadCellDef->cd_labels; sl != NULL; sl = sl->lab_next)
{
idx = sl->lab_port;
if (idx > i) i = idx;
if ((idx > 0) && (sl != lab) && !strcmp(sl->lab_text, textbody))
{
i = idx - 1;
break;
}
}
i++;
portnum = i;
flags |= PORT_DIR_NORTH | PORT_DIR_SOUTH |
PORT_DIR_EAST | PORT_DIR_WEST;
freeMagic((char *)lab);
break;
}
}
sl = lab;
}
if (font < 0)
lab = DBPutLabel(cifReadCellDef, &r, pos, textbody, type, flags, portnum);
lab = DBPutLabel(cifReadCellDef, &r, pos, textbody, type, flags);
else
lab = DBPutFontLabel(cifReadCellDef, &r, font, size, angle,
&GeoOrigin, pos, textbody, type, flags, portnum);
&GeoOrigin, pos, textbody, type, flags);
if ((lab != NULL) && (cifnum >= 0) &&
(cifCurReadStyle->crs_labelSticky[cifnum] == LABEL_TYPE_PORT))
{
Label *sl;
int idx;
/* No port information can be encoded in the GDS file, so */
/* assume defaults, and assume that the port order is the */
/* order in which labels arrive in the GDS stream. If */
/* ports have the same text, then give them the same index. */
/* order in which labels arrive in the GDS stream. */
i = -1;
for (sl = cifReadCellDef->cd_labels; sl != NULL; sl = sl->lab_next)
{
idx = sl->lab_port;
idx = sl->lab_flags & PORT_NUM_MASK;
if (idx > i) i = idx;
if ((idx > 0) && (sl != lab) && !strcmp(sl->lab_text, textbody))
{
i = idx - 1;
break;
}
}
i++;
lab->lab_port = i;
lab->lab_flags |= (PORT_NUM_MASK & i);
lab->lab_flags |= PORT_DIR_NORTH | PORT_DIR_SOUTH |
PORT_DIR_EAST | PORT_DIR_WEST;
}
@ -1090,7 +925,7 @@ calmaElementText(void)
/* done with textbody */
if (textbody != NULL) freeMagic(textbody);
}
/*
* ----------------------------------------------------------------------------
*
@ -1102,24 +937,26 @@ calmaElementText(void)
* centerline, to avoid roundoff errors.
*
* Results:
* non-NULL CIFPath* the caller takes ownership of
* if the path was parsed successfully, otherwise NULL.
* TRUE is returned if the path was parsed successfully,
* FALSE otherwise.
*
* Side effects:
* None
* Modifies the parameter pathheadpp to point to the path
* that is constructed.
*
* ----------------------------------------------------------------------------
*/
CIFPath *
calmaReadPath(
int iscale)
bool
calmaReadPath(pathheadpp, iscale)
CIFPath **pathheadpp;
int iscale;
{
CIFPath path, *pathheadp, *pathtailp, *newpathp;
CIFPath path, *pathtailp, *newpathp;
int nbytes, rtype, npoints, savescale;
bool nonManhattan = FALSE;
pathheadp = (CIFPath *) NULL;
*pathheadpp = (CIFPath *) NULL;
pathtailp = (CIFPath *) NULL;
path.cifp_next = (CIFPath *) NULL;
@ -1127,13 +964,13 @@ calmaReadPath(
READRH(nbytes, rtype);
if (nbytes < 0)
{
CalmaReadError("EOF when reading path.\n");
return (NULL);
calmaReadError("EOF when reading path.\n");
return (FALSE);
}
if (rtype != CALMA_XY)
{
calmaUnexpected(CALMA_XY, rtype);
return (NULL);
return (FALSE);
}
/* Read this many points (pairs of four-byte integers) */
@ -1144,7 +981,7 @@ calmaReadPath(
calmaReadPoint(&path.cifp_point, iscale);
if (savescale != calmaReadScale1)
{
CIFPath *phead = pathheadp;
CIFPath *phead = *pathheadpp;
int newscale = calmaReadScale1 / savescale;
while (phead != NULL)
{
@ -1154,13 +991,13 @@ calmaReadPath(
}
}
if (ABS(path.cifp_x) > 0x0fffffff || ABS(path.cifp_y) > 0x0fffffff) {
CalmaReadError("Warning: Very large point in path: (%d, %d)\n",
calmaReadError("Warning: Very large point in path: (%d, %d)\n",
path.cifp_x, path.cifp_y);
}
if (FEOF(calmaInputFile))
if (feof(calmaInputFile))
{
CIFFreePath(pathheadp);
return (NULL);
CIFFreePath(*pathheadpp);
return (FALSE);
}
if (iscale != 0)
@ -1168,7 +1005,7 @@ calmaReadPath(
newpathp = (CIFPath *) mallocMagic((unsigned) (sizeof (CIFPath)));
*newpathp = path;
if (pathheadp)
if (*pathheadpp)
{
/*
* Check that this segment is Manhattan. If not, remember the
@ -1189,13 +1026,13 @@ calmaReadPath(
}
pathtailp->cifp_next = newpathp;
}
else pathheadp = newpathp;
else *pathheadpp = newpathp;
pathtailp = newpathp;
}
}
return (pathheadp);
return (*pathheadpp != NULL);
}
/*
* ----------------------------------------------------------------------------
*
@ -1218,29 +1055,20 @@ calmaReadPath(
*/
void
calmaLayerError(
char *mesg,
int layer,
int dt)
calmaLayerError(mesg, layer, dt)
char *mesg;
int layer;
int dt;
{
CalmaLayerType clt;
HashEntry *he;
/* Ignore errors for cells that are marked as read-only, since */
/* these are normally expected to have unhandled layer types, */
/* since the purpose of read-only cells is to preserve exactly */
/* layout in the cell which may not be represented in the tech */
/* file. */
if ((cifReadCellDef->cd_flags & CDVENDORGDS) == CDVENDORGDS)
return;
clt.clt_layer = layer;
clt.clt_type = dt;
he = HashFind(&calmaLayerHash, (char *) &clt);
if (HashGetValue(he) == NULL)
{
HashSetValue(he, (ClientData) 1);
CalmaReadError("%s, layer=%d type=%d\n", mesg, layer, dt);
calmaReadError("%s, layer=%d type=%d\n", mesg, layer, dt);
}
}

View File

@ -3,24 +3,23 @@
*
* Input of Calma GDS-II stream format.
*
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
*/
#ifndef lint
static const char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magic-8.0/calma/CalmaRead.c,v 1.3 2010/06/24 12:37:15 tim Exp $";
static char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magic-8.0/calma/CalmaRead.c,v 1.3 2010/06/24 12:37:15 tim Exp $";
#endif /* not lint */
#include <stdarg.h>
#include <stdio.h>
#include <string.h>
#include <sys/types.h>
@ -28,12 +27,6 @@ static const char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magi
#include <netinet/in.h>
/*
* C99 compat
* Mind: tcltk/tclmagic.h must be included prior to all the other headers
*/
#include "tcltk/tclmagic.h"
#include "utils/magic.h"
#include "utils/geometry.h"
#include "tiles/tile.h"
@ -53,17 +46,14 @@ static const char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magi
#include "textio/textio.h"
#include "calma/calmaInt.h"
#include "commands/commands.h" /* for CmdGetRootPoint */
#include "utils/main.h" /* for EditCellUse */
#include "utils/undo.h"
/* C99 compat */
#include "calma/calma.h"
/* Globals for Calma reading */
FILETYPE calmaInputFile = NULL; /* Read from this stream */
FILE *calmaInputFile = NULL; /* Read from this stream */
FILE *calmaErrorFile = NULL; /* Write error output here */
unsigned char CalmaSubcellPolygons = CALMA_POLYGON_NONE;
/* Read non-Manhattan polygons as-is */
bool CalmaSubcellPolygons = FALSE; /* Put non-Manhattan polygons
* in their own subcells.
*/
int CalmaPolygonCount;
bool CalmaSubcellPaths = FALSE; /* Put paths in their own subcells. */
int CalmaPathCount;
@ -73,21 +63,10 @@ bool CalmaFlattenUses = FALSE; /* If TRUE, small cells in the input
* performance when handling contacts
* saved as subcell arrays.
*/
char **CalmaFlattenUsesByName = NULL; /* NULL-terminated list of strings
* to do glob-style pattern matching
* to determine what cells to flatten
* by cellname.
*/
bool CalmaReadOnly = FALSE; /* Set files to read-only and
* retain file position information
* so cells can be written verbatim.
*/
float CalmaMagScale = 1.0; /* Scale by which to interpret the MAG
* record in GDS text records. The
* default is to treat the value as
* the text height in microns. This
* value reinterprets the scale.
*/
bool CalmaNoDRCCheck = FALSE; /* If TRUE, don't mark cells as needing
* a DRC check; they will be assumed
* DRC clean.
@ -98,21 +77,9 @@ bool CalmaPostOrder = FALSE; /* If TRUE, forces the GDS parser to
* flatten cells that are contact cuts.
* Added by Nishit 8/16/2004
*/
bool CalmaNoDuplicates = FALSE; /* If TRUE, then if a cell exists in
* memory with the same name as a cell
* in the GDS file, then the cell in
* the GDS file is skipped.
*/
bool CalmaUnique = FALSE; /* If TRUE, then if a cell exists in
* memory with the same name as a cell
* in the GDS file, then the cell in
* memory is renamed to a unique
* identifier with a _N suffix.
*/
extern bool CalmaDoLibrary; /* Also used by GDS write */
extern void calmaUnexpected();
extern void calmaUnexpected(int wanted, int got);
extern int calmaWriteInitFunc(CellDef *def);
bool calmaParseUnits();
/*
* Scaling.
@ -147,8 +114,8 @@ HashTable calmaLayerHash;
HashTable calmaDefInitHash;
/* Common stuff to ignore */
const int calmaElementIgnore[] = { CALMA_ELFLAGS, CALMA_PLEX, -1 };
int calmaElementIgnore[] = { CALMA_ELFLAGS, CALMA_PLEX, -1 };
/*
* ----------------------------------------------------------------------------
*
@ -167,24 +134,18 @@ const int calmaElementIgnore[] = { CALMA_ELFLAGS, CALMA_PLEX, -1 };
*/
void
CalmaReadFile(
FILETYPE file, /* File from which to read Calma */
char *filename) /* The real name of the file read */
CalmaReadFile(file, filename)
FILE *file; /* File from which to read Calma */
char *filename; /* The real name of the file read */
{
int k, version;
char *libname = NULL, *libnameptr = NULL;
char *libname = NULL;
MagWindow *mw;
static const int hdrSkip[] = { CALMA_FORMAT, CALMA_MASK, CALMA_ENDMASKS,
CALMA_REFLIBS, CALMA_FONTS, CALMA_ATTRTABLE,
CALMA_STYPTABLE, CALMA_GENERATIONS, -1 };
static const int skipBeforeLib[] = { CALMA_LIBDIRSIZE, CALMA_SRFNAME,
CALMA_LIBSECUR, -1 };
if (EditCellUse == (CellUse *)NULL)
{
TxError("Cannot read GDS: There is no edit cell.\n");
return;
}
static int hdrSkip[] = { CALMA_FORMAT, CALMA_MASK, CALMA_ENDMASKS,
CALMA_REFLIBS, CALMA_FONTS, CALMA_ATTRTABLE,
CALMA_STYPTABLE, CALMA_GENERATIONS, -1 };
static int skipBeforeLib[] = { CALMA_LIBDIRSIZE, CALMA_SRFNAME,
CALMA_LIBSECUR, -1 };
/* We will use full cell names as keys in this hash table */
CIFReadCellInit(0);
@ -211,12 +172,6 @@ CalmaReadFile(
CalmaPolygonCount = 0;
CalmaPathCount = 0;
/* Reset cd_client pointers (using init function from CalmaWrite.c) */
/* This is in case a cell already in memory is being referenced; */
/* it is probably better to avoid those kinds of naming collisions */
/* though. . . */
(void) DBCellSrDefs(0, calmaWriteInitFunc, (ClientData) NULL);
HashInit(&calmaDefInitHash, 32, 0);
calmaLApresent = FALSE;
calmaInputFile = file;
@ -226,48 +181,20 @@ CalmaReadFile(
if (version < 600)
TxPrintf("Library written using GDS-II Release %d.0\n", version);
else
TxPrintf("Library written using GDS-II Release %d.%d\n",
TxPrintf("Library written using GDS-II Release %d.%d\n",
version / 100, version % 100);
if (!calmaSkipExact(CALMA_BGNLIB)) goto done;
calmaSkipSet(skipBeforeLib);
if (!calmaReadStringRecord(CALMA_LIBNAME, &libname)) goto done;
/* Use CalmaDoLibrary similarly for input as for output; if set to */
/* TRUE, the library name is considered meaningless and discarded; */
/* the GDS file contents are read into memory but no view is loaded */
if (CalmaDoLibrary)
libnameptr = NULL;
else
libnameptr = libname;
if ((libnameptr != NULL) && (libname[0] != '\0'))
if ((libname != NULL) && (libname[0] != '\0'))
{
bool modified = FALSE;
char *sptr;
/* Avoid generating a magic name with spaces in it. . . */
/* (added by Mike Godfrey, 7/17/05) */
for (k = 0; k < strlen(libname); k++)
if (libname[k] == ' ')
{
libname[k] = '_';
modified = TRUE;
}
/* Avoid generating a magic name with slashes in it. . . */
/* (added by Tim, 8/26/2022) */
if ((sptr = strrchr(libname, '/')) != NULL)
{
libnameptr = sptr + 1;
modified = TRUE;
}
if (modified)
TxPrintf("Library name modified to make legal cell name syntax.\n");
TxPrintf("Library name: %s\n", libnameptr);
TxPrintf("Library name: %s\n", libname);
}
/* Skip the reflibs, fonts, etc. cruft */
@ -292,28 +219,24 @@ done:
/* top-level cell, so magic-produced GDS can be read back */
/* with the expected cell appearing in the layout window. */
if (libnameptr != NULL)
if (libname != NULL)
{
mw = CmdGetRootPoint((Point *)NULL, (Rect *)NULL);
if (mw == NULL)
windCheckOnlyWindow(&mw, DBWclientID);
if (mw != NULL)
{
if (calmaLookCell(libnameptr) != (CellDef *)NULL)
DBWloadWindow(mw, libnameptr, 0);
if (calmaLookCell(libname, NULL) != (CellDef *)NULL)
DBWloadWindow(mw, libname, FALSE);
}
freeMagic(libname);
}
CIFReadCellCleanup(FILE_CALMA);
CIFReadCellCleanup(1);
HashKill(&calmaDefInitHash);
UndoEnable();
if (calmaErrorFile != NULL)
{
fclose(calmaErrorFile);
calmaErrorFile = NULL;
}
if (calmaErrorFile != NULL) fclose(calmaErrorFile);
}
/*
@ -347,13 +270,12 @@ done:
*/
bool
calmaParseUnits(void)
calmaParseUnits()
{
int nbytes, rtype = 0;
int nbytes, rtype;
double metersPerDBUnit;
double userUnitsPerDBUnit;
double cuPerDBUnit;
bool compatible;
READRH(nbytes, rtype);
#ifdef lint
@ -372,39 +294,6 @@ calmaParseUnits(void)
/* Read meters per database unit */
if (!calmaReadR8(&metersPerDBUnit)) return (FALSE);
/* Important! When CalmaReadOnly is TRUE, then this file will have its
* contents output verbatim. But if the database units don't match,
* then it will get output at the wrong scale. Setting a magnification
* factor on the instance when generating output might (?) work. For
* now, prohibiting a GDS read in read-only mode when the database units
* don't match. This forces the user either to reconsider the read-only
* status or to rewrite the GDS at a compatible scalefactor.
*/
compatible = TRUE;
if (CalmaReadOnly == TRUE)
{
if (CIFCurStyle->cs_flags & CWF_ANGSTROMS)
{
if ((int)(0.5 + metersPerDBUnit * 1e12) != 100)
{
CalmaReadError("Incompatible scale factor of %g, must be 1e-10.\n",
metersPerDBUnit);
TxError("Cannot read this file in read-only mode.\n");
return FALSE;
}
}
else
{
if ((int)(0.5 + metersPerDBUnit * 1e11) != 100)
{
CalmaReadError("Incompatible scale factor of %g, must be 1e-9.\n",
metersPerDBUnit);
TxError("Cannot read this file in read-only mode.\n");
return FALSE;
}
}
}
#ifdef notdef
TxPrintf("1 database unit equals %e user units\n", userUnitsPerDBUnit);
TxPrintf("1 database unit equals %e meters\n", metersPerDBUnit);
@ -437,11 +326,11 @@ calmaParseUnits(void)
return (TRUE);
}
/*
* ----------------------------------------------------------------------------
*
* CalmaReadError --
* calmaReadError --
*
* This procedure is called to print out error messages during
* Calma file reading.
@ -459,38 +348,31 @@ calmaParseUnits(void)
*/
void
CalmaReadError(const char *format, ...)
/*VARARGS1*/
calmaReadError(format, a1, a2, a3, a4, a5, a6, a7, a8, a9, a10)
char *format;
char *a1, *a2, *a3, *a4, *a5, *a6, *a7, *a8, *a9, *a10;
{
va_list args;
OFFTYPE filepos;
calmaTotalErrors++;
if (CIFWarningLevel == CIF_WARN_NONE) return;
if ((calmaTotalErrors < 100) || (CIFWarningLevel != CIF_WARN_LIMIT))
{
filepos = FTELL(calmaInputFile);
{
if (CIFWarningLevel == CIF_WARN_REDIRECT)
{
if (calmaErrorFile != NULL)
{
fprintf(calmaErrorFile, "Error while reading cell \"%s\" ",
fprintf(calmaErrorFile, "Error while reading cell \"%s\": ",
cifReadCellDef->cd_name);
fprintf(calmaErrorFile, "(byte position %"DLONG_PREFIX"d): ",
(dlong)filepos);
va_start(args, format);
Vfprintf(calmaErrorFile, format, args);
va_end(args);
fprintf(calmaErrorFile, format, a1, a2, a3, a4, a5, a6, a7,
a8, a9, a10);
}
}
else
{
TxError("Error while reading cell \"%s\" ", cifReadCellDef->cd_name);
TxError("(byte position %"DLONG_PREFIX"d): ", (dlong)filepos);
va_start(args, format);
TxErrorV(format, args);
va_end(args);
TxError("Error while reading cell \"%s\": ", cifReadCellDef->cd_name);
TxError(format, a1, a2, a3, a4, a5, a6, a7, a8, a9, a10);
}
}
else if ((calmaTotalErrors == 100) && (CIFWarningLevel == CIF_WARN_LIMIT))
@ -498,7 +380,7 @@ CalmaReadError(const char *format, ...)
TxError("Error limit set: Remaining errors will not be reported.\n");
}
}
/*
* ----------------------------------------------------------------------------
*
@ -516,11 +398,11 @@ CalmaReadError(const char *format, ...)
*/
void
calmaUnexpected(
int wanted, /* Type of record we wanted */
int got) /* Type of record we got */
calmaUnexpected(wanted, got)
int wanted; /* Type of record we wanted */
int got; /* Type of record we got */
{
CalmaReadError("Unexpected record type in input: \n");
calmaReadError("Unexpected record type in input: \n");
if (CIFWarningLevel == CIF_WARN_NONE) return;
if (calmaTotalErrors < 100 || (CIFWarningLevel != CIF_WARN_LIMIT))
@ -541,7 +423,7 @@ calmaUnexpected(
}
}
}
/*
* ----------------------------------------------------------------------------
*
@ -558,12 +440,12 @@ calmaUnexpected(
* ----------------------------------------------------------------------------
*/
const char *
calmaRecordName(
int rtype)
char *
calmaRecordName(rtype)
int rtype;
{
static char numeric[10];
static const char * const calmaRecordNames[] =
static char *calmaRecordNames[] =
{
"HEADER", "BGNLIB", "LIBNAME", "UNITS",
"ENDLIB", "BGNSTR", "STRNAME", "ENDSTR",
@ -590,7 +472,7 @@ calmaRecordName(
return (calmaRecordNames[rtype]);
}
/*
* ----------------------------------------------------------------------------
*
@ -608,28 +490,8 @@ calmaRecordName(
*/
void
CalmaTechInit(void)
CalmaTechInit()
{
ASSERT(sizeof(FourByteInt)==4, "definition in calmaInt.h");
ASSERT(sizeof(TwoByteInt)==2, "definition in calmaInt.h");
/* NOTE: Add "$$*$$" to the default "flatglob" value */
/* when CalmaContactArrays behaves like the non-arrayed */
/* function and can be enabled by default. */
/* Initialize CalmaFlattenByName to have one entry for */
/* "*_CDNS_*" to match the name style used by many foundry */
/* cells and which corresponds to pcells that often split */
/* layers between cells in ways that magic can't cope with; */
/* and whose original parameterized functions cannot be */
/* recovered by magic anyway. When necessary, this default */
/* can be overridden by the "gds flatglob none" command */
/* option. */
if (CalmaFlattenUsesByName == (char **)NULL)
{
CalmaFlattenUsesByName = (char **)mallocMagic(2 * sizeof(char *));
*CalmaFlattenUsesByName = StrDup((char **)NULL, "*_CDNS_*");
*(CalmaFlattenUsesByName + 1) = NULL;
}
}

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

30
calma/Depend Normal file
View File

@ -0,0 +1,30 @@
CalmaRead.o: CalmaRead.c ../utils/magic.h ../utils/geometry.h \
../tiles/tile.h ../utils/utils.h ../utils/hash.h ../database/database.h \
../database/databaseInt.h ../utils/malloc.h ../utils/tech.h ../cif/cif.h \
../cif/CIFint.h ../cif/CIFread.h ../utils/signals.h ../windows/windows.h \
../dbwind/dbwind.h ../utils/styles.h ../textio/textio.h \
../calma/calmaInt.h ../commands/commands.h ../utils/undo.h
CalmaRdcl.o: CalmaRdcl.c ../utils/magic.h ../utils/geometry.h \
../tiles/tile.h ../utils/utils.h ../utils/hash.h ../database/database.h \
../database/databaseInt.h ../utils/malloc.h ../utils/tech.h ../cif/cif.h \
../cif/CIFint.h ../cif/CIFread.h ../utils/signals.h ../windows/windows.h \
../dbwind/dbwind.h ../utils/styles.h ../textio/textio.h \
../calma/calmaInt.h ../calma/calma.h
CalmaRdio.o: CalmaRdio.c ../utils/magic.h ../utils/geometry.h \
../tiles/tile.h ../utils/utils.h ../utils/hash.h ../database/database.h \
../database/databaseInt.h ../utils/malloc.h ../utils/tech.h ../cif/cif.h \
../cif/CIFint.h ../cif/CIFread.h ../utils/signals.h ../windows/windows.h \
../dbwind/dbwind.h ../utils/styles.h ../textio/textio.h \
../calma/calmaInt.h
CalmaRdpt.o: CalmaRdpt.c ../utils/magic.h ../utils/geometry.h \
../tiles/tile.h ../utils/utils.h ../utils/hash.h ../database/database.h \
../database/databaseInt.h ../utils/malloc.h ../utils/tech.h ../cif/cif.h \
../cif/CIFint.h ../cif/CIFread.h ../utils/signals.h ../windows/windows.h \
../dbwind/dbwind.h ../utils/styles.h ../textio/textio.h \
../calma/calmaInt.h ../calma/calma.h
CalmaWrite.o: CalmaWrite.c ../utils/magic.h ../utils/malloc.h \
../utils/geometry.h ../tiles/tile.h ../utils/utils.h ../utils/hash.h \
../database/database.h ../database/databaseInt.h ../utils/tech.h \
../cif/cif.h ../cif/CIFint.h ../utils/signals.h ../windows/windows.h \
../dbwind/dbwind.h ../utils/styles.h ../textio/textio.h \
../calma/calmaInt.h ../utils/main.h ../utils/stack.h

View File

@ -4,7 +4,7 @@
MODULE = calma
MAGICDIR = ..
SRCS = CalmaRead.c CalmaRdcl.c CalmaRdio.c CalmaRdpt.c CalmaWrite.c CalmaWriteZ.c
SRCS = CalmaRead.c CalmaRdcl.c CalmaRdio.c CalmaRdpt.c CalmaWrite.c
include ${MAGICDIR}/defs.mak
include ${MAGICDIR}/rules.mak

View File

@ -4,97 +4,43 @@
* This file defines things that are exported by the
* calma module to the rest of the world.
*
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
*
* rcsid $Header: /usr/cvsroot/magic-8.0/calma/calma.h,v 1.1.1.1 2008/02/03 20:43:50 tim Exp $
*/
#ifndef _MAGIC__CALMA__CALMA_H
#define _MAGIC__CALMA__CALMA_H
#ifndef _CALMA_H
#define _CALMA_H
#include "utils/magic.h"
/* Externally visible variables */
extern unsigned char CalmaSubcellPolygons;
extern bool CalmaSubcellPolygons;
extern bool CalmaSubcellPaths;
extern bool CalmaDoLabels;
extern bool CalmaDoLibrary;
extern bool CalmaDoLower;
extern bool CalmaAddendum;
extern bool CalmaNoDuplicates;
extern time_t *CalmaDateStamp;
extern bool CalmaUnique;
extern TileTypeBitMask *CalmaMaskHints;
extern bool CalmaMergeTiles;
extern bool CalmaFlattenArrays;
extern bool CalmaNoDRCCheck;
extern bool CalmaFlattenUses;
extern int CalmaFlattenLimit;
extern float CalmaMagScale;
extern char **CalmaFlattenUsesByName;
extern bool CalmaReadOnly;
extern bool CalmaContactArrays;
#ifdef HAVE_ZLIB
extern int CalmaCompression;
#endif
extern bool CalmaPostOrder;
extern bool CalmaAllowUndefined;
extern bool CalmaAllowAbstract;
/* Definitions used by the return value for CalmaSubcellPolygons */
/* CALMA_POLYGON_NONE: Process polygons immediately */
/* CALMA_POLYGON_TEMP: Create temporary polygon subcells */
/* CALMA_POLYGON_KEEP: Keep polygons in subcells */
#define CALMA_POLYGON_NONE 0
#define CALMA_POLYGON_TEMP 1
#define CALMA_POLYGON_KEEP 2
/* Externally-visible procedures: */
extern bool CalmaWrite(CellDef *rootDef, FILE *f);
extern void CalmaReadFile(FILETYPE file, char *filename);
extern void CalmaTechInit(void);
extern bool CalmaGenerateArray(FILE *f, TileType type, int llx, int lly, int pitch, int cols, int rows);
extern void CalmaReadError(const char *format, ...) ATTR_FORMAT_PRINTF_1;
extern bool CalmaWrite();
extern void CalmaReadFile();
extern void CalmaTechInit();
extern bool CalmaGenerateArray();
/* C99 compat */
extern void calmaDelContacts(void);
extern void calmaElementBoundary(void);
extern void calmaElementBox(void);
extern void calmaElementPath(void);
extern void calmaElementText(void);
extern bool calmaIsUseNameDefault(char *defName, char *useName);
extern bool calmaParseStructure(char *filename);
extern int calmaProcessDef(CellDef *def, FILE *outf, bool do_library);
#ifdef HAVE_ZLIB
extern int calmaProcessDefZ(CellDef *def, gzFile outf, bool do_library);
#endif
extern bool calmaReadI2Record(int type, int *pvalue);
extern bool calmaReadI4Record(int type, int *pvalue);
extern void calmaReadPoint(Point *p, int iscale);
extern bool calmaReadR8(double *pd);
extern bool calmaReadStampRecord(int type, int *stampptr);
extern bool calmaReadStringRecord(int type, char **str);
extern bool calmaReadStringRecord(int type, char **str);
extern bool calmaReadTransform(Transform *ptrans, char *name);
extern bool calmaSkipBytes(int nbytes);
extern bool calmaSkipExact(int type);
extern bool calmaSkipTo(int what);
extern void calmaUnexpected(int wanted, int got);
#ifdef HAVE_ZLIB
extern bool CalmaWriteZ(CellDef *rootDef, gzFile f);
extern bool CalmaGenerateArrayZ(gzFile f, TileType type, int llx, int lly, int pitch, int cols, int rows);
#endif
#endif /* _MAGIC__CALMA__CALMA_H */
#endif /* _CALMA_H */

View File

@ -4,23 +4,23 @@
* This file defines constants used internally by the calma
* module, but not exported to the rest of the world.
*
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
*
* rcsid $Header: /usr/cvsroot/magic-8.0/calma/calmaInt.h,v 1.2 2010/06/24 12:37:15 tim Exp $
*/
#ifndef _MAGIC__CALMA__CALMAINT_H
#define _MAGIC__CALMA__CALMAINT_H
#ifndef _CALMAINT_H
#define _CALMAINT_H
#include "utils/magic.h"
#include "database/database.h"
@ -99,7 +99,6 @@
#define CALMA_NUMRECORDTYPES 60 /* Number of above types */
/* Property types defined for magic */
#define CALMA_PROP_USENAME_STD 61 /* To record non-default cell use ids */
#define CALMA_PROP_USENAME 98 /* To record non-default cell use ids */
#define CALMA_PROP_ARRAY_LIMITS 99 /* To record non-default array limits */
@ -131,17 +130,10 @@ typedef struct
/* Length of record header */
#define CALMAHEADERLENGTH 4
/* Label types
* The intention is all the values can be stored/converted with unsigned char type,
* C23 allows us to be explicit with the type but C99 does not, so a comment for now.
*/
typedef enum /* : unsigned char */ { LABEL_TYPE_NONE, LABEL_TYPE_TEXT, LABEL_TYPE_PORT, LABEL_TYPE_CELLID } labelType;
/* ------------------------- Input macros ----------------------------- */
/* Globals for Calma reading */
extern FILETYPE calmaInputFile;
extern FILE *calmaInputFileNoCompression;
extern FILE *calmaInputFile;
extern char *calmaFilename;
extern int calmaReadScale1;
extern int calmaReadScale2;
@ -162,7 +154,7 @@ extern int calmaLArtype;
# define ntohs(x) (x)
# define htonl(x) (x)
# define htons(x) (x)
# endif
# endif
#endif
typedef union { char uc[2]; unsigned short us; } TwoByteInt;
@ -172,8 +164,8 @@ typedef union { char uc[4]; unsigned int ul; } FourByteInt;
#define READI2(z) \
{ \
TwoByteInt u; \
u.uc[0] = FGETC(calmaInputFile); \
u.uc[1] = FGETC(calmaInputFile); \
u.uc[0] = getc(calmaInputFile); \
u.uc[1] = getc(calmaInputFile); \
(z) = (int) ntohs(u.us); \
}
@ -181,10 +173,10 @@ typedef union { char uc[4]; unsigned int ul; } FourByteInt;
#define READI4(z) \
{ \
FourByteInt u; \
u.uc[0] = FGETC(calmaInputFile); \
u.uc[1] = FGETC(calmaInputFile); \
u.uc[2] = FGETC(calmaInputFile); \
u.uc[3] = FGETC(calmaInputFile); \
u.uc[0] = getc(calmaInputFile); \
u.uc[1] = getc(calmaInputFile); \
u.uc[2] = getc(calmaInputFile); \
u.uc[3] = getc(calmaInputFile); \
(z) = (int) ntohl(u.ul); \
}
@ -197,10 +189,10 @@ typedef union { char uc[4]; unsigned int ul; } FourByteInt;
calmaLApresent = FALSE; \
} else { \
READI2(nb); \
if (FEOF(calmaInputFile)) nb = -1; \
if (feof(calmaInputFile)) nb = -1; \
else { \
(rt) = FGETC(calmaInputFile); \
(void) FGETC(calmaInputFile); \
(rt) = getc(calmaInputFile); \
(void) getc(calmaInputFile); \
} \
} \
}
@ -219,52 +211,19 @@ typedef union { char uc[4]; unsigned int ul; } FourByteInt;
UNREADRH(nb, rt); \
}
/* Structure used for sorting ports by number */
typedef struct portlabel
{
Label *pl_label;
unsigned int pl_port;
} PortLabel;
/* Other commonly used globals */
extern HashTable calmaLayerHash;
extern const int calmaElementIgnore[];
extern CellDef *calmaFindCell(const char *name, bool *was_called, bool *predefined);
extern int calmaElementIgnore[];
extern CellDef *calmaFindCell();
/* (Added by Nishit, 8/18/2004--8/24/2004) */
extern CellDef *calmaLookCell(char *name);
extern void calmaWriteContacts(FILE *f);
extern CellDef *calmaGetContactCell(TileType type, bool lookOnly);
extern CellDef *calmaLookCell();
extern void calmaWriteContact();
extern CellDef *calmaGetContactCell();
extern bool calmaIsContactCell;
extern const char *calmaRecordName(int rtype);
extern void calmaSkipSet(const int *skipwhat);
extern bool calmaParseUnits(void);
extern int compport(const void *one, const void *two);
#define LB_EXTERNAL 0 /* Polygon external edge */
#define LB_INTERNAL 1 /* Polygon internal edge */
#define LB_INIT 2 /* Data not yet valid */
typedef struct LB1 {
char lb_type; /* Boundary Type (external or internal) */
Point lb_start; /* Start point */
struct LB1 *lb_next; /* Next point record */
} LinkedBoundary;
typedef struct BT1 {
LinkedBoundary *bt_first; /* Polygon list */
int bt_points; /* Number of points in this list */
struct BT1 *bt_next; /* Next polygon record */
} BoundaryTop;
extern int calmaAddSegment(LinkedBoundary **lbptr, bool poly_edge, int p1x, int p1y, int p2x, int p2y);
extern void calmaMergeSegments(LinkedBoundary *edge, BoundaryTop **blist, int num_points);
extern void calmaRemoveDegenerate(BoundaryTop *blist);
extern void calmaRemoveColinear(BoundaryTop *blist);
extern char *calmaRecordName();
extern void calmaSkipSet();
/* ------------------- Imports from CIF reading ----------------------- */
@ -274,4 +233,4 @@ extern Plane **cifCurReadPlanes;
extern HashTable CifCellTable;
extern Plane *cifEditCellPlanes[];
#endif /* _MAGIC__CALMA__CALMAINT_H */
#endif /* _CALMAINT_H */

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

View File

@ -4,23 +4,23 @@
* Defines things shared internally by the cif module of Magic,
* but not generally needed outside the cif module.
*
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
*
* rcsid "$Header: /usr/cvsroot/magic-8.0/cif/CIFint.h,v 1.3 2008/12/04 17:10:29 tim Exp $"
*/
#ifndef _MAGIC__CIF__CIFINT_H
#define _MAGIC__CIF__CIFINT_H
#ifndef _CIFINT_H
#define _CIFINT_H
#include "database/database.h"
@ -46,17 +46,11 @@
typedef struct bloat_data
{
int bl_plane; /* Plane on which a bloat or squares
* operation is valid. If -1, then the bloat
* types are CIF types.
* operation is valid.
*/
int bl_distance[TT_MAXTYPES];
} BloatData;
typedef struct bridge_data
{
int br_width; /* Minimum width rule for bridge */
} BridgeData;
typedef struct squares_data
{
int sq_border;
@ -75,7 +69,6 @@ typedef struct slots_data
int sl_lsize;
int sl_lsep;
int sl_offset;
int sl_start;
} SlotsData;
typedef struct cifop
@ -86,9 +79,8 @@ typedef struct cifop
* below for the legal ones.
*/
int co_distance; /* Grow or shrink distance (if needed). */
ClientData co_client; /* Pointer to a BloatData, SquaresData,
* SlotsData, or BridgeData structure,
* or NULL.
ClientData co_client; /* Pointer to a BloatData, SquaresData, or
* SlotsData structure, or NULL.
*/
struct cifop *co_next; /* Next in list of operations to perform. */
} CIFOp;
@ -103,7 +95,6 @@ typedef struct cifop
* the masks.
* CIFOP_GROW - Grow the current results uniformly by co_distance.
* CIFOP_GROW_G - Grow the current results to snap to the indicated grid.
* CIFOP_GROWMIN - Grow result such that no dimension is less than co_distance.
* CIFOP_SHRINK - Shrink the current results uniformly by co_distance.
* CIFOP_BLOAT - Find layers in paintMask, then bloat selectively
* according to bl_distance, and OR the results into
@ -130,52 +121,32 @@ typedef struct cifop
* the cell bounding box. This involves no magic type
* layers but may itself be acted upon with grow/shrink
* rules.
* CIFOP_BOUNDARY - Added 6/5/19---map the FIXED_BBOX property bounding
* box coordinates into CIF layer geometry.
* CIFOP_NET - Added 11/3/08---pull an entire electrical net into
* the CIF layer, selectively picking layers.
* CIFOP_MAXRECT - Reduce all disjoint regions to the largest internal fitting
* CIFOP_MAXRECT - Reduce all areas to the largest internal fitting
* rectangle.
* CIFOP_INTERACT - Select all disjoint regions which overlap a given set of types
* CIFOP_COPYUP - Added 5/5/16---make and keep a copy the resulting layer,
* which will be painted into parent cells instead of the
* current cell. This replaces the "fault" method.
* CIFOP_CLOSE - Added 11/25/19---close up areas smaller than indicated
* CIFOP_MANHATTAN - Added 3/27/25---remove or fill nonmanhattan areas
* CIFOP_BRIDGE - Added 6/11/20---Bridge across catecorner gaps
* CIFOP_BRIDGELIM - Added 27/07/20---Bridge across catecorner gaps, but with limiting layers
* CIFOP_MASKHINTS - Added 12/14/20---Add geometry from cell properties, if any.
*/
#define CIFOP_AND 1
#define CIFOP_OR 2
#define CIFOP_GROW 3
#define CIFOP_GROWMIN 4
#define CIFOP_GROW_G 5
#define CIFOP_SHRINK 6
#define CIFOP_BLOAT 7
#define CIFOP_SQUARES 8
#define CIFOP_SLOTS 9
#define CIFOP_BLOATMAX 10
#define CIFOP_BLOATMIN 11
#define CIFOP_BLOATALL 12
#define CIFOP_ANDNOT 13
#define CIFOP_SQUARES_G 14
#define CIFOP_BBOX 15
#define CIFOP_BOUNDARY 16
#define CIFOP_NET 17
#define CIFOP_MAXRECT 18
#define CIFOP_INTERACT 19
#define CIFOP_COPYUP 20
#define CIFOP_CLOSE 21
#define CIFOP_MANHATTAN 22
#define CIFOP_BRIDGE 23
#define CIFOP_BRIDGELIM 24
#define CIFOP_MASKHINTS 25
/* Definitions of bit fields used in the value of co_client for CIFOP_INTERACT */
#define CIFOP_INT_NOT 0x1 /* Inverted sense (not interacting) */
#define CIFOP_INT_TOUCHING 0x2 /* Include both touching and overlapping */
#define CIFOP_GROW_G 4
#define CIFOP_SHRINK 5
#define CIFOP_BLOAT 6
#define CIFOP_SQUARES 7
#define CIFOP_SLOTS 8
#define CIFOP_BLOATMAX 9
#define CIFOP_BLOATMIN 10
#define CIFOP_BLOATALL 11
#define CIFOP_ANDNOT 12
#define CIFOP_SQUARES_G 13
#define CIFOP_BBOX 14
#define CIFOP_NET 15
#define CIFOP_MAXRECT 16
#define CIFOP_COPYUP 17
/* Added by Tim 10/21/2004 */
/* The following structure is used to pass information on how to draw
@ -219,7 +190,7 @@ typedef struct
*/
int min_width; /* the minimum width rule in centi-microns
* for the layer. This is used by Grow Sliver
* to generate drc correct parent slivers
* to generate drc correct parent slivers
*/
#ifdef THREE_D
int cl_renderStyle; /* Style to render CIF layer with */
@ -233,12 +204,12 @@ typedef struct
*
* CIF_TEMP: Means that this is a temporary layer used to build
* up CIF information. It isn't output in the CIF file.
* CIF_LABEL: This layer is used to generate fixed labels in the
* output file.
* CIF_BBOX_TOP: Indicates that the bounding box rectangle should
* only be generated if the cell is a top-level cell.
*/
#define CIF_TEMP 1
#define CIF_LABEL 2
#define CIF_BBOX_TOP 2
/* The following data structure describes a complete set of CIF
* layers. The number of CIF layers (MAXCIFLAYERS) must not be
@ -279,7 +250,7 @@ typedef struct cifstyle
* file more readable). Default of 1.
* Unused for GDS input/output.
*/
int cs_expander; /* cs_scaleFactor / cs_expander = scale in
int cs_expander; /* cs_scaleFactor / cs_expander = scale in
* centimicrons. Default of 1. Value 10
* means cs_scaleFactor is measured in
* nanometers (millimicrons)
@ -301,12 +272,9 @@ typedef struct cifstyle
* layer.
*/
int cs_portLayer[TT_MAXTYPES];
/* Similar to cs_labelLayer, to use as
* a type for geometry attached to port labels.
*/
int cs_portText[TT_MAXTYPES];
/* Similar to cs_labelLayer, to use as
* a text type for port labels
/* Similar to cs_labelLayer, to distinguish
* between output types used for "normal"
* text and those used specifically for ports.
*/
CIFLayer *cs_layers[MAXCIFLAYERS];
/* Describes how to generate each layer.*/
@ -319,57 +287,32 @@ typedef struct cifstyle
#define CWF_GROW_SLIVERS 0x02
#define CWF_ANGSTROMS 0x04
#define CWF_GROW_EUCLIDEAN 0x08
#define CWF_SEE_NO_VENDOR 0x10 /* Hide magic's GDS from vendor cells */
#define CWF_NO_ERRORS 0x20 /* Do not generate error msgs and fdbk */
#define CWF_STRING_LIMIT 0x40 /* Use older Calma format character limit */
#define CWF_MINIMUM_GRID 0x80 /* Force minimum grid scaling */
#define CWF_SEE_VENDOR 0x10 /* Override vendor GDS flag in cells */
#define CWF_NO_ERRORS 0x20 /* Do not generate error msgs and fdbk */
/* procedures */
extern bool CIFNameToMask(char *name, TileTypeBitMask *result, TileTypeBitMask *depend);
extern void CIFGenSubcells(CellDef *def, Rect *area, Plane **output);
extern void CIFGenArrays(CellDef *def, Rect *area, Plane **output);
extern void CIFGen(CellDef *cellDef, CellDef *origDef, const Rect *area, Plane **planes, TileTypeBitMask *layers,
bool replace, bool genAllPlanes, bool hier, ClientData clientdata);
extern void CIFClearPlanes(Plane **planes);
extern Plane *CIFGenLayer(CIFOp *op, const Rect *area, CellDef *cellDef, CellDef *origDef, Plane *temps[],
bool hier, ClientData clientdata);
extern void CIFInitCells(void);
extern int cifHierCopyFunc(Tile *tile, TreeContext *cxp);
extern int cifHierCopyMaskHints(SearchContext *scx, ClientData clientData);
extern void CIFLoadStyle(char *stylename);
extern void CIFCopyMaskHints(SearchContext *scx, CellDef *targetDef);
/* C99 compat */
extern void CIFCoverageLayer(CellDef *rootDef, Rect *area, char *layer, bool dolist);
extern bool CIFWriteFlat(CellDef *rootDef, FILE *f);
extern void CIFScalePlanes(int scalen, int scaled, Plane **planearray);
extern void CIFInputRescale(int n, int d);
extern int CIFScaleCoord(int cifCoord, int snap_type);
extern int cifGrowSliver(Tile *tile, Rect *area);
extern int cifHierElementFunc(CellUse *use, Transform *transform, int x, int y, Rect *checkArea);
extern int cifSquareFunc(Rect *area, CIFOp *op, int *rows, int *columns, Rect *cut);
extern int cifSquareGridFunc(Rect *area, CIFOp *op, int *rows, int *columns, Rect *cut);
extern int cifSlotFunc(Rect *area, CIFOp *op, int *numY, int *numX, Rect *cut, bool vertical);
extern int CIFParseScale(char *true_scale, int *expander);
extern int cifParseCalmaNums(char *str, int *numArray, int numNums);
extern bool CIFReadTechLimitScale(int ns, int ds);
extern bool CIFNameToMask();
extern void CIFGenSubcells();
extern void CIFGenArrays();
extern void CIFGen();
extern void CIFClearPlanes();
extern Plane *CIFGenLayer();
extern void CIFInitCells();
extern int cifHierCopyFunc();
extern void CIFLoadStyle();
/* Shared variables and structures: */
extern Plane *CIFPlanes[]; /* Normal place to store CIF. */
extern CIFKeep *CIFStyleList; /* List of all CIF styles. */
extern CIFStyle *CIFCurStyle; /* Current style being used. */
extern CIFStyle *CIFDRCStyle; /* CIF style for DRC checking (optional) */
extern CellUse *CIFComponentUse; /* Flatten stuff in here if needed. */
extern CellDef *CIFComponentDef; /* Corresponds to CIFComponentUse. */
extern CellUse *CIFDummyUse; /* Used to dummy up a CellUse for a
* def.
*/
extern Plane *CIFTotalPlanes[]; /* Exported for diagnostics */
extern Plane *CIFComponentPlanes[]; /* Exported for diagnostics */
/* Valid values of CIFWarningLevel (see cif.h) */
typedef enum {CIF_WARN_DEFAULT, CIF_WARN_NONE, CIF_WARN_ALIGN,
@ -384,13 +327,13 @@ extern int CIFHierRects;
/* Tables used for painting and erasing CIF. */
extern const PaintResultType CIFPaintTable[], CIFEraseTable[];
extern PaintResultType CIFPaintTable[], CIFEraseTable[];
/* Procedures and variables for reporting errors. */
extern int CIFErrorLayer;
extern CellDef *CIFErrorDef;
extern void CIFError(Rect *area, char *message);
extern void CIFError();
/* The following determines the tile type used to hold the CIF
* information on its paint plane.
@ -399,4 +342,4 @@ extern void CIFError(Rect *area, char *message);
#define CIF_SOLIDTYPE 1
extern TileTypeBitMask CIFSolidBits;
#endif /* _MAGIC__CIF__CIFINT_H */
#endif /* _CIFINT_H */

View File

@ -3,21 +3,21 @@
* This file contains global information for the CIF module,
* such as performance statistics.
*
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
*/
#ifndef lint
static const char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magic-8.0/cif/CIFmain.c,v 1.3 2009/01/15 15:44:34 tim Exp $";
static char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magic-8.0/cif/CIFmain.c,v 1.3 2009/01/15 15:44:34 tim Exp $";
#endif /* not lint */
#include <stdio.h>
@ -76,7 +76,7 @@ static int cifTotalHierRects = 0;
global CellDef *CIFErrorDef; /* Definition in which to record errors. */
global int CIFErrorLayer; /* Index of CIF layer associated with errors.*/
/*
* ----------------------------------------------------------------------------
*
@ -95,7 +95,7 @@ global int CIFErrorLayer; /* Index of CIF layer associated with errors.*/
*/
void
CIFPrintStats(void)
CIFPrintStats()
{
TxPrintf("CIF statistics (recent/total):\n");
cifTotalTileOps += CIFTileOps;
@ -128,7 +128,7 @@ CIFPrintStats(void)
* Results:
* Internal units-to-(nanometers * convert) conversion factor (float).
* Use convert = 1000 for centimicrons-to-microns conversion
*
*
* Side effects:
* None.
*
@ -136,8 +136,8 @@ CIFPrintStats(void)
*/
float
CIFGetOutputScale(
int convert)
CIFGetOutputScale(convert)
int convert;
{
if (CIFCurStyle == NULL) return 1.0;
@ -145,28 +145,6 @@ CIFGetOutputScale(
(float)(CIFCurStyle->cs_expander * convert));
}
/*
* ----------------------------------------------------------------------------
*
* CIFGetScale --
*
* Same as the above routine, but provides the scalefactor to get CIF
* units from centimicrons (which generally means just returning the
* expander value to show if units have been declared in nanometers or
* angstroms).
*
* ----------------------------------------------------------------------------
*/
float
CIFGetScale(
int convert)
{
if (CIFCurStyle == NULL) return 1.0;
return (1.0 / (float)(CIFCurStyle->cs_expander * convert));
}
/*
* ----------------------------------------------------------------------------
*
@ -185,10 +163,10 @@ CIFGetScale(
*/
void
CIFPrintStyle(
bool dolist, /* Return as a list if true */
bool doforall, /* Print all known styles if true */
bool docurrent) /* Print current style if true */
CIFPrintStyle(dolist, doforall, docurrent)
bool dolist; /* Return as a list if true */
bool doforall; /* Print all known styles if true */
bool docurrent; /* Print current style if true */
{
CIFKeep *style;
@ -234,7 +212,7 @@ CIFPrintStyle(
}
}
/*
* ----------------------------------------------------------------------------
*
@ -254,13 +232,12 @@ CIFPrintStyle(
*/
void
CIFSetStyle(
char *name) /* Name of the new style. If NULL, just
CIFSetStyle(name)
char *name; /* Name of the new style. If NULL, just
* print out the valid styles.
*/
{
CIFKeep *style, *match, *exactmatch;
bool ambiguous = FALSE;
CIFKeep *style, *match;
int length;
if (name == NULL) return;
@ -270,25 +247,18 @@ CIFSetStyle(
for (style = CIFStyleList; style != NULL; style = style->cs_next)
{
if (!strcmp(name, style->cs_name)) {
match = style;
ambiguous = FALSE;
break;
}
else if (!strncmp(name, style->cs_name, length))
if (strncmp(name, style->cs_name, length) == 0)
{
if (match != NULL) ambiguous = TRUE;
if (match != NULL)
{
TxError("CIF output style \"%s\" is ambiguous.\n", name);
CIFPrintStyle(FALSE, TRUE, TRUE);
return;
}
match = style;
}
}
if (ambiguous)
{
TxError("CIF output style \"%s\" is ambiguous.\n", name);
CIFPrintStyle(FALSE, TRUE, TRUE);
return;
}
if (match != NULL)
{
CIFLoadStyle(match->cs_name);
@ -299,7 +269,7 @@ CIFSetStyle(
TxError("\"%s\" is not one of the CIF output styles Magic knows.\n", name);
CIFPrintStyle(FALSE, TRUE, TRUE);
}
/*
* ----------------------------------------------------------------------------
*
@ -320,10 +290,10 @@ CIFSetStyle(
*/
bool
CIFNameToMask(
char *name,
TileTypeBitMask *result,
TileTypeBitMask *depend)
CIFNameToMask(name, result, depend)
char *name;
TileTypeBitMask *result;
TileTypeBitMask *depend;
{
int i, j;
CIFOp *op;
@ -357,23 +327,7 @@ CIFNameToMask(
{
cl = CIFCurStyle->cs_layers[j];
for (op = cl->cl_ops; op != NULL; op = op->co_next)
{
TTMaskSetMask(depend, &op->co_cifMask);
/* Bloat layers may depend on CIF layers */
/* Currently supported only with bloat-all */
if (op->co_opcode == CIFOP_BLOATALL)
{
BloatData *bloats = (BloatData *)op->co_client;
TileType ttype;
if (bloats->bl_plane < 0) /* Use CIF types */
for (ttype = 0; ttype < TT_MAXTYPES; ttype++)
if (bloats->bl_distance[ttype] > 0)
TTMaskSetType(depend, ttype);
}
}
}
}
return TRUE;
@ -392,7 +346,7 @@ CIFNameToMask(
TxError(".\n");
return FALSE;
}
/*
* ----------------------------------------------------------------------------
*
@ -414,11 +368,11 @@ CIFNameToMask(
*/
void
CIFError(
Rect *area, /* Place in CIFErrorDef where there was a
CIFError(area, message)
Rect *area; /* Place in CIFErrorDef where there was a
* problem in generating CIFErrorLayer.
*/
char *message) /* Short note about what went wrong. */
char *message; /* Short note about what went wrong. */
{
char msg[200];
@ -431,7 +385,7 @@ CIFError(
DBWFeedbackAdd(area, msg, CIFErrorDef, CIFCurStyle->cs_scaleFactor,
STYLE_PALEHIGHLIGHTS);
}
/*
* ----------------------------------------------------------------------------
*
@ -452,7 +406,7 @@ CIFError(
*/
int
CIFOutputScaleFactor(void)
CIFOutputScaleFactor()
{
if (CIFCurStyle == NULL) return 1;
return CIFCurStyle->cs_scaleFactor;

View File

@ -5,21 +5,21 @@
* both definitions and calls, and user-defined features
* like labels.
*
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
*/
#ifndef lint
static const char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magic-8.0/cif/CIFrdcl.c,v 1.5 2010/08/25 17:33:55 tim Exp $";
static char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magic-8.0/cif/CIFrdcl.c,v 1.5 2010/08/25 17:33:55 tim Exp $";
#endif /* not lint */
#include <stdio.h>
@ -103,7 +103,7 @@ typedef struct {
*/
char *cifSubcellId = NULL;
/*
* ----------------------------------------------------------------------------
*
@ -126,8 +126,8 @@ char *cifSubcellId = NULL;
*/
void
CIFReadCellInit(
int ptrkeys)
CIFReadCellInit(ptrkeys)
int ptrkeys;
{
int i;
@ -150,7 +150,7 @@ CIFReadCellInit(
* cifForgetCell --
*
* This local procedure is used to find a cell in the subcell
* table and remove its CellDef entry.
* table and remove its CellDef entry.
*
* Results:
* FALSE if no such entry was found, otherwise TRUE.
@ -162,8 +162,8 @@ CIFReadCellInit(
*/
bool
cifForgetCell(
int cifNum)
cifForgetCell(cifNum)
int cifNum;
{
HashEntry *h;
@ -196,8 +196,8 @@ cifForgetCell(
*/
void
cifUniqueCell(
int cifNum)
cifUniqueCell(cifNum)
int cifNum;
{
HashEntry *h;
CellDef *def, *testdef;
@ -234,7 +234,7 @@ cifUniqueCell(
CIFReadError("Warning: cell definition %d reused.\n", cifNum);
}
/*
* ----------------------------------------------------------------------------
*
@ -256,8 +256,8 @@ cifUniqueCell(
*/
CellDef *
cifFindCell(
int cifNum) /* The CIF number of the desired cell. */
cifFindCell(cifNum)
int cifNum; /* The CIF number of the desired cell. */
{
HashEntry *h;
CellDef *def, *testdef;
@ -273,7 +273,7 @@ cifFindCell(
def = DBCellLookDef(name);
if (def == NULL)
{
def = DBCellNewDef(name);
def = DBCellNewDef(name, (char *) NULL);
/* Tricky point: call DBReComputeBbox here to make SURE
* that the cell has a valid bounding box. Otherwise,
@ -299,10 +299,10 @@ cifFindCell(
*/
void
CIFScalePlanes(
int scalen,
int scaled,
Plane **planearray)
CIFScalePlanes(scalen, scaled, planearray)
int scalen;
int scaled;
Plane **planearray;
{
int pNum;
Plane *newplane;
@ -346,11 +346,10 @@ CIFScalePlanes(
*
* ----------------------------------------------------------------------------
*/
void
CIFInputRescale(
int n,
int d)
CIFInputRescale(n, d)
int n, d;
{
CIFReadStyle *istyle = cifCurReadStyle;
CIFReadLayer *cl;
@ -387,10 +386,8 @@ CIFInputRescale(
}
}
CIFScalePlanes(n, d, cifCurReadPlanes);
if (cifCurReadPlanes != cifEditCellPlanes)
CIFScalePlanes(n, d, cifEditCellPlanes);
if ((const Plane*)cifEditCellPlanes != (const Plane*)cifSubcellPlanes && cifCurReadPlanes != cifSubcellPlanes)
CIFScalePlanes(n, d, cifEditCellPlanes);
if (cifEditCellPlanes != cifSubcellPlanes)
CIFScalePlanes(n, d, cifSubcellPlanes);
CIFReadWarning("CIF style %s: units rescaled by factor of %d / %d\n",
@ -418,10 +415,10 @@ CIFInputRescale(
*/
bool
CIFParseStart(void)
CIFParseStart()
{
int number;
if (cifSubcellBeingRead)
{
CIFReadError("definition start inside other definition; ignored.\n");
@ -492,7 +489,7 @@ CIFParseStart(void)
cifCurReadPlanes = cifSubcellPlanes;
return TRUE;
}
/*
* ----------------------------------------------------------------------------
@ -503,9 +500,9 @@ CIFParseStart(void)
* ----------------------------------------------------------------------------
*/
int cifCheckPaintFunc(
Tile *tile,
ClientData clientData)
int cifCheckPaintFunc(tile, clientData)
Tile *tile;
ClientData clientData;
{
return 1;
}
@ -513,9 +510,9 @@ int cifCheckPaintFunc(
/* Callback function for copying paint from one CIF cell into another */
int
cifCopyPaintFunc(
Tile *tile,
CIFCopyRec *cifCopyRec)
cifCopyPaintFunc(tile, cifCopyRec)
Tile *tile;
CIFCopyRec *cifCopyRec;
{
int pNum;
TileType dinfo;
@ -541,40 +538,6 @@ cifCopyPaintFunc(
return 0;
}
/*
* ----------------------------------------------------------------------------
*
* cifMaskHintFunc --
*
* For each tile in the scanned plane, convert the tile into a coordinate
* string by appending the coordinates to the list passed as clientData.
*
* Results:
* Return 0 to keep the search going.
*
* Side effects:
* Allocates memory for and seeds a linked rect entry
*
* ----------------------------------------------------------------------------
*/
int
cifMaskHintFunc(
Tile *tile,
LinkedRect **lrecp)
{
Rect r;
LinkedRect *newlr;
newlr = (LinkedRect *)mallocMagic(sizeof(LinkedRect));
newlr->r_next = *lrecp;
(*lrecp) = newlr;
TiToRect(tile, &newlr->r_r);
return 0;
}
/*
* ----------------------------------------------------------------------------
*
@ -594,24 +557,20 @@ cifMaskHintFunc(
*/
int
CIFPaintCurrent(
int filetype)
CIFPaintCurrent()
{
extern int cifMakeBoundaryFunc(Tile *tile, ClientData clientdata); /* Forward declaration. */
extern int cifPaintCurrentFunc(Tile *tile, TileType type); /* Forward declaration. */
Plane *plane, *swapplane;
int i;
for (i = 0; i < cifCurReadStyle->crs_nLayers; i++)
{
TileType type;
extern int cifPaintCurrentFunc(); /* Forward declaration. */
CIFOp *op;
plane = CIFGenLayer(cifCurReadStyle->crs_layers[i]->crl_ops,
&TiPlaneRect, (CellDef *)NULL, (CellDef *)NULL,
cifCurReadPlanes, FALSE, (ClientData)NULL);
&TiPlaneRect, (CellDef *) NULL, cifCurReadPlanes);
/* Generate a paint/erase table, then paint from the CIF
* plane into the current Magic cell.
*/
@ -640,13 +599,13 @@ CIFPaintCurrent(
Plane **parray;
extern char *(cifReadLayers[MAXCIFRLAYERS]);
/* NOTE: The condition cd_client == 0 when CDFLATGDS
* indicates that the cell was already in memory when the
* GDS was read. This condition should be properly caught
* and handled.
/* NOTE: There should be no need to check for cd_client
* here as cd_client should not be CLIENTDEFAULT if CDFLATGDS
* is set in flags. This condition has occurred, though, and
* needs to be debugged.
*/
if ((cifReadCellDef->cd_flags & CDFLATGDS) &&
(cifReadCellDef->cd_client != (ClientData)0))
if ((cifReadCellDef->cd_flags & CDFLATGDS) &&
(cifReadCellDef->cd_client != (ClientData)CLIENTDEFAULT))
parray = (Plane **)cifReadCellDef->cd_client;
else
{
@ -682,23 +641,6 @@ CIFPaintCurrent(
}
}
}
else if (op == NULL)
{
/* Handle boundary layer */
op = cifCurReadStyle->crs_layers[i]->crl_ops;
while (op)
{
if (op->co_opcode == CIFOP_BOUNDARY) break;
op = op->co_next;
}
if (op && (DBSrPaintArea((Tile *)NULL, plane, &TiPlaneRect,
&DBAllButSpaceBits, cifCheckPaintFunc,
(ClientData)NULL) == 1))
DBSrPaintArea((Tile *) NULL, plane, &TiPlaneRect,
&CIFSolidBits, cifMakeBoundaryFunc, INT2CD(filetype));
}
/* Swap planes */
swapplane = cifCurReadPlanes[type];
@ -709,175 +651,15 @@ CIFPaintCurrent(
{
DBSrPaintArea((Tile *) NULL, plane, &TiPlaneRect,
&CIFSolidBits, cifPaintCurrentFunc,
INT2CD(type));
(ClientData)type);
}
/* Recycle the plane, which was dynamically allocated. */
DBFreePaintPlane(plane);
TiFreePlane(plane);
}
/* If mask hints were requested, then for each GDS/CIF layer in the */
/* input, if the layer has a corresponding output layer and the */
/* output layer has a mask hints operator, then generate the output */
/* plane for that layer, compare to the input plane, and create */
/* mask hint properties to make the output the same as the input. */
if ((CalmaMaskHints != NULL) && (!TTMaskIsZero(CalmaMaskHints)))
{
int j;
CIFOp *op, newop, subop;
Plane *presult;
TileTypeBitMask genMask;
int *in_out_map;
extern char *(cifReadLayers[MAXCIFRLAYERS]);
TTMaskZero(&genMask);
in_out_map = (int *)mallocMagic(cifNReadLayers * sizeof(int));
for (i = 0; i < cifNReadLayers; i++)
{
if (!TTMaskHasType(CalmaMaskHints, i)) continue;
/* Does the input layer have a corresponding output layer? */
in_out_map[i] = -1;
for (j = 0; j < CIFCurStyle->cs_nLayers; j++)
{
if (!strcmp(CIFCurStyle->cs_layers[j]->cl_name, cifReadLayers[i]))
{
/* Does the layer have a mask-hints operator? */
for (op = CIFCurStyle->cs_layers[j]->cl_ops; op; op = op->co_next)
if (op->co_opcode == CIFOP_MASKHINTS)
{
TTMaskSetType(&genMask, j);
in_out_map[i] = j;
break;
}
}
if (in_out_map[i] >= 0) break;
}
}
/* Multiply input planes to the same scale as the generated output */
CIFScalePlanes(CIFCurStyle->cs_scaleFactor, cifCurReadStyle->crs_scaleFactor,
cifCurReadPlanes);
/* Generate the output for these layers from the cell contents */
CIFClearPlanes(CIFPlanes);
/* TO-DO: Replace DBAllTypeBits with genMask. Requires that genMask */
/* be expanded to include all dependent layers. */
CIFGen(cifReadCellDef, cifReadCellDef, &TiPlaneRect, CIFPlanes, &DBAllTypeBits,
TRUE, FALSE, FALSE, (ClientData)NULL);
/* Set up double operator for OR and ANDNOT functions */
newop.co_opcode = CIFOP_OR;
newop.co_distance = 0;
newop.co_next = &subop;
newop.co_client = (ClientData)NULL;
TTMaskZero(&newop.co_paintMask);
subop.co_opcode = CIFOP_ANDNOT;
subop.co_distance = 0;
subop.co_next = NULL;
subop.co_client = (ClientData)NULL;
TTMaskZero(&subop.co_paintMask);
for (i = 0; i < cifNReadLayers; i++)
{
LinkedRect *lrec = NULL;
char *propstr = NULL;
char locstr[512];
Plane *tempp;
if (!TTMaskHasType(CalmaMaskHints, i)) continue;
j = in_out_map[i];
if (j < 0) continue;
TTMaskSetOnlyType(&subop.co_cifMask, j);
/* Replace last layer + 1 on CIFPlanes with input layer i */
tempp = CIFPlanes[CIFCurStyle->cs_nLayers];
TTMaskSetOnlyType(&newop.co_cifMask, CIFCurStyle->cs_nLayers);
CIFPlanes[CIFCurStyle->cs_nLayers] = cifCurReadPlanes[i];
CIFCurStyle->cs_nLayers++;
/* Compute result (i AND-NOT j), which will be all the areas of
* the input on layer i that are not generated by writing output
* layer j.
*/
presult = CIFGenLayer(&newop, &TiPlaneRect, (CellDef *)NULL,
(CellDef *)NULL, CIFPlanes, FALSE, (ClientData)NULL);
/* Scan the resulting plane and generate linked Rect structures for
* each shape found.
*/
DBSrPaintArea((Tile *)NULL, presult, &TiPlaneRect, &CIFSolidBits,
cifMaskHintFunc, (ClientData)&lrec);
if (lrec != NULL)
{
char *propname;
propname = (char *)mallocMagic(11 + strlen(cifReadLayers[i]));
sprintf(propname, "MASKHINTS_%s", cifReadLayers[i]);
propstr = (char *)NULL;
/* Turn all linked Rects into a mask-hints property in the
* target cell.
*/
while (lrec != NULL)
{
char *newstr;
sprintf(locstr, "%d %d %d %d",
lrec->r_r.r_xbot / CIFCurStyle->cs_scaleFactor,
lrec->r_r.r_ybot / CIFCurStyle->cs_scaleFactor,
lrec->r_r.r_xtop / CIFCurStyle->cs_scaleFactor,
lrec->r_r.r_ytop / CIFCurStyle->cs_scaleFactor);
if (propstr == NULL)
{
newstr = (char *)mallocMagic(strlen(locstr) + 1);
sprintf(newstr, "%s", locstr);
}
else
{
newstr = (char *)mallocMagic(strlen(locstr)
+ strlen(propstr) + 2);
sprintf(newstr, "%s %s", propstr, locstr);
freeMagic(propstr);
}
propstr = newstr;
free_magic1_t mm1 = freeMagic1_init();
freeMagic1(&mm1, lrec);
lrec = lrec->r_next;
freeMagic1_end(&mm1);
}
/* NOTE: propstr is transferred to the CellDef and should
* not be free'd here.
*/
DBPropPut(cifReadCellDef, propname, propstr);
freeMagic(propname);
}
/* Delete the generated plane */
DBFreePaintPlane(presult);
TiFreePlane(presult);
/* Replace the input plane that was shuffled out */
CIFCurStyle->cs_nLayers--;
CIFPlanes[CIFCurStyle->cs_nLayers] = tempp;
}
/* Free up the planes used to create the output */
CIFClearPlanes(CIFPlanes);
freeMagic((char *)in_out_map);
}
/* Now go through all the current planes and zero them out. */
for (i = 0; i < MAXCIFRLAYERS; i++)
@ -886,91 +668,14 @@ CIFPaintCurrent(
return 0;
}
/* Use CIF layer geometry to define a fixed bounding box for the current cell */
/* Below is the search function invoked for each CIF tile type
* found for the current layer.
*/
int
cifMakeBoundaryFunc(
Tile *tile, /* Tile of CIF information. */
ClientData clientdata) /* Pass the file type (CIF or CALMA) */
{
/* It is assumed that there is one rectangle for the boundary. */
/* If there are multiple rectangles defined with the boundary */
/* layer, then the last one defines the FIXED_BBOX property. */
Rect area;
char propertyvalue[128], *storedvalue;
int savescale;
int filetype = (int)CD2INT(clientdata);
TiToRect(tile, &area);
area.r_xtop = CIFScaleCoord(area.r_xtop, COORD_EXACT);
savescale = cifCurReadStyle->crs_scaleFactor;
area.r_ytop = CIFScaleCoord(area.r_ytop, COORD_EXACT);
if (savescale != cifCurReadStyle->crs_scaleFactor)
{
area.r_xtop *= (savescale / cifCurReadStyle->crs_scaleFactor);
savescale = cifCurReadStyle->crs_scaleFactor;
}
area.r_xbot = CIFScaleCoord(area.r_xbot, COORD_EXACT);
if (savescale != cifCurReadStyle->crs_scaleFactor)
{
area.r_xtop *= (savescale / cifCurReadStyle->crs_scaleFactor);
area.r_ytop *= (savescale / cifCurReadStyle->crs_scaleFactor);
savescale = cifCurReadStyle->crs_scaleFactor;
}
area.r_ybot = CIFScaleCoord(area.r_ybot, COORD_EXACT);
if (savescale != cifCurReadStyle->crs_scaleFactor)
{
area.r_xtop *= (savescale / cifCurReadStyle->crs_scaleFactor);
area.r_ytop *= (savescale / cifCurReadStyle->crs_scaleFactor);
area.r_xbot *= (savescale / cifCurReadStyle->crs_scaleFactor);
}
if (cifReadCellDef->cd_flags & CDFIXEDBBOX)
{
char *propvalue;
bool found;
/* Only flag a warning if the redefined boundary was */
/* different from the original. */
propvalue = (char *)DBPropGet(cifReadCellDef, "FIXED_BBOX", &found);
if (found)
{
Rect bbox;
if (sscanf(propvalue, "%d %d %d %d", &bbox.r_xbot, &bbox.r_ybot,
&bbox.r_xtop, &bbox.r_ytop) == 4)
{
if ((bbox.r_xbot != area.r_xbot) ||
(bbox.r_ybot != area.r_ybot) ||
(bbox.r_xtop != area.r_xtop) ||
(bbox.r_ytop != area.r_ytop))
{
if (filetype == FILE_CIF)
CIFReadError("Warning: Cell %s boundary was redefined.\n",
cifReadCellDef->cd_name);
else
CalmaReadError("Warning: Cell %s boundary was redefined.\n",
cifReadCellDef->cd_name);
}
}
}
}
sprintf(propertyvalue, "%d %d %d %d",
area.r_xbot, area.r_ybot, area.r_xtop, area.r_ytop);
storedvalue = StrDup((char **)NULL, propertyvalue);
DBPropPut(cifReadCellDef, "FIXED_BBOX", storedvalue);
cifReadCellDef->cd_flags |= CDFIXEDBBOX;
return 0;
}
/* Paint CIF layer geometry into the current cell def as magic layer "type" */
int
cifPaintCurrentFunc(
Tile *tile, /* Tile of CIF information. */
TileType type) /* Magic type to be painted. */
cifPaintCurrentFunc(tile, type)
Tile *tile; /* Tile of CIF information. */
TileType type; /* Magic type to be painted. */
{
Rect area;
int pNum;
@ -1025,7 +730,7 @@ cifPaintCurrentFunc(
return 0; /* To keep the search alive. */
}
/*
* ----------------------------------------------------------------------------
*
@ -1045,7 +750,7 @@ cifPaintCurrentFunc(
*/
bool
CIFParseFinish(void)
CIFParseFinish()
{
if (!cifSubcellBeingRead)
{
@ -1053,12 +758,12 @@ CIFParseFinish(void)
CIFSkipToSemi();
return FALSE;
}
if (cifSubcellId != NULL)
if (cifSubcellId != NULL)
{
CIFReadError("pending call identifier %s discarded.\n", cifSubcellId);
(void) StrDup(&cifSubcellId, (char *) NULL);
}
/* Take the `F'. */
TAKE();
@ -1067,8 +772,8 @@ CIFParseFinish(void)
* the appropriate cell of the database. Then restore the saved
* layer info.
*/
CIFPaintCurrent(FILE_CIF);
CIFPaintCurrent();
DBAdjustLabels(cifReadCellDef, &TiPlaneRect);
DBReComputeBbox(cifReadCellDef);
@ -1080,7 +785,7 @@ CIFParseFinish(void)
cifCurReadPlanes = cifEditCellPlanes;
return TRUE;
}
/*
* ----------------------------------------------------------------------------
*
@ -1100,7 +805,7 @@ CIFParseFinish(void)
*/
bool
CIFParseDelete(void)
CIFParseDelete()
{
int number;
@ -1120,7 +825,7 @@ CIFParseDelete(void)
CIFSkipToSemi();
return TRUE;
}
/*
* ----------------------------------------------------------------------------
*
@ -1142,7 +847,7 @@ CIFParseDelete(void)
*/
char *
cifParseName(void)
cifParseName()
{
char ch;
char *bufferp;
@ -1152,7 +857,7 @@ cifParseName(void)
for (ch = PEEK() ; ch == ' ' || ch == '\t' ; ch = PEEK())
TAKE();
/* Read the string. */
bufferp = &buffer[0];
@ -1163,7 +868,7 @@ cifParseName(void)
*bufferp = '\0';
return buffer;
}
/*
* ----------------------------------------------------------------------------
*
@ -1184,7 +889,7 @@ cifParseName(void)
*/
bool
cifParseUser9(void)
cifParseUser9()
{
char *name;
@ -1196,7 +901,7 @@ cifParseUser9(void)
}
return TRUE;
}
/*
* ----------------------------------------------------------------------------
*
@ -1216,13 +921,13 @@ cifParseUser9(void)
*/
bool
CIFParseCall(void)
CIFParseCall()
{
int called;
Transform transform;
CellUse *use;
CellDef *def;
/* Take the `C'. */
TAKE();
@ -1261,7 +966,7 @@ CIFParseCall(void)
(void) StrDup(&cifSubcellId, (char *) NULL);
return TRUE;
}
/*
* ----------------------------------------------------------------------------
*
@ -1283,7 +988,7 @@ CIFParseCall(void)
*/
bool
cifParseUser91(void)
cifParseUser91()
{
if (cifSubcellId != NULL)
{
@ -1293,7 +998,7 @@ cifParseUser91(void)
(void) StrDup(&cifSubcellId, cifParseName());
return TRUE;
}
/*
* ----------------------------------------------------------------------------
*
@ -1314,7 +1019,7 @@ cifParseUser91(void)
*/
bool
cifParseUser94(void)
cifParseUser94()
{
Rect rectangle;
char *name = NULL;
@ -1346,7 +1051,7 @@ cifParseUser94(void)
* current cell. Tricky business: in order for the default
* label location to be computed
*/
CIFSkipBlanks();
if (PEEK() != ';')
{
@ -1378,12 +1083,12 @@ cifParseUser94(void)
flags = LABEL_STICKY;
else
flags = 0;
(void) DBPutLabel(cifReadCellDef, &rectangle, -1, name, type, flags, 0);
(void) DBPutLabel(cifReadCellDef, &rectangle, -1, name, type, flags);
}
freeMagic(name);
return TRUE;
}
/*
* ----------------------------------------------------------------------------
*
@ -1404,7 +1109,7 @@ cifParseUser94(void)
*/
bool
cifParseUser95(void)
cifParseUser95()
{
/* Modified by BIM 1/8/2018 */
Rect rectangle;
@ -1422,12 +1127,12 @@ cifParseUser95(void)
CIFSkipToSemi();
return FALSE;
}
savescale = cifCurReadStyle->crs_scaleFactor;
/* The center coordinates returned are in CIF units *2 */
/* the values will be halved later before conversion to magic units */
if (! CIFParsePoint(&center, 2))
{
CIFReadError("95 command, but no location; ignored.\n");
@ -1451,10 +1156,10 @@ cifParseUser95(void)
lowerleft.p_x = center.p_x - size.p_x;
lowerleft.p_y = center.p_y - size.p_y;
upperright.p_x = center.p_x + size.p_x;
upperright.p_y = center.p_y + size.p_y;
if ((lowerleft.p_x % 2 == 0) && (lowerleft.p_y % 2 == 0)) {
/* if possible convert values to CIF units by dividing by two */
@ -1472,9 +1177,9 @@ cifParseUser95(void)
CIFInputRescale(2, 1);
}
/* now scale each of the co-ordinates in turn */
lowerleft.p_x = CIFScaleCoord(lowerleft.p_x, COORD_ANY);
savescale = cifCurReadStyle->crs_scaleFactor;
@ -1539,13 +1244,13 @@ cifParseUser95(void)
flags = LABEL_STICKY;
else
flags = 0;
(void) DBPutLabel(cifReadCellDef, &rectangle, -1, name, type, flags, 0);
(void) DBPutLabel(cifReadCellDef, &rectangle, -1, name, type, flags);
}
freeMagic(name);
return TRUE;
}
/*
* ----------------------------------------------------------------------------
*
@ -1564,7 +1269,7 @@ cifParseUser95(void)
* ----------------------------------------------------------------------------
*/
bool
CIFParseUser(void)
CIFParseUser()
{
char ch;
@ -1593,7 +1298,7 @@ CIFParseUser(void)
return FALSE;
}
}
/*
* ----------------------------------------------------------------------------
*
@ -1616,8 +1321,8 @@ CIFParseUser(void)
*/
void
CIFReadCellCleanup(
int filetype)
CIFReadCellCleanup(type)
int type; // 0 = CIF, 1 = GDS, because routine is used by both
{
HashEntry *h;
HashSearch hs;
@ -1627,10 +1332,10 @@ CIFReadCellCleanup(
if (cifSubcellBeingRead)
{
if (filetype == FILE_CIF)
if (type == 0)
CIFReadError("CIF ended partway through a symbol definition.\n");
else
CalmaReadError("GDS ended partway through a symbol definition.\n");
calmaReadError("GDS ended partway through a symbol definition.\n");
(void) CIFParseFinish();
}
@ -1643,36 +1348,32 @@ CIFReadCellCleanup(
def = (CellDef *) HashGetValue(h);
if (def == NULL)
{
if (filetype == FILE_CIF)
if (type == 0)
CIFReadError("cell table has NULL entry (Magic error).\n");
else
CalmaReadError("cell table has NULL entry (Magic error).\n");
calmaReadError("cell table has NULL entry (Magic error).\n");
continue;
}
flags = def->cd_flags;
if (!(flags & CDAVAILABLE))
{
if (filetype == FILE_CIF)
if (type == 0)
CIFReadError("cell %s was used but not defined.\n", def->cd_name);
else
CalmaReadError("cell %s was used but not defined.\n", def->cd_name);
calmaReadError("cell %s was used but not defined.\n", def->cd_name);
}
def->cd_flags &= ~CDPROCESSEDGDS;
if ((filetype == FILE_CIF && CIFNoDRCCheck == FALSE) ||
(filetype == FILE_CALMA && CalmaNoDRCCheck == FALSE))
if ((type == 0 && CIFNoDRCCheck == FALSE) ||
(type == 1 && CalmaNoDRCCheck == FALSE))
DRCCheckThis(def, TT_CHECKPAINT, &def->cd_bbox);
DBWAreaChanged(def, &def->cd_bbox, DBW_ALLWINDOWS, &DBAllButSpaceBits);
DBCellSetModified(def, TRUE);
/* Only mark cell as needing a timestamp update if the timestamp is zero */
if (def->cd_timestamp != 0)
def->cd_flags &= ~CDGETNEWSTAMP;
}
/* Do geometrical processing on the top-level cell. */
CIFPaintCurrent(FILE_CIF);
CIFPaintCurrent();
DBAdjustLabels(EditCellUse->cu_def, &TiPlaneRect);
DBReComputeBbox(EditCellUse->cu_def);
DBWAreaChanged(EditCellUse->cu_def, &EditCellUse->cu_def->cd_bbox,
@ -1693,32 +1394,54 @@ CIFReadCellCleanup(
if (def->cd_flags & CDFLATGDS)
{
/* These cells have been flattened and are no longer needed. */
/* Do not remove the actual CellDef, though, because it is */
/* still instanced, and that instance tells the GDS write */
/* routine that the subcell needs to be included in the */
/* output. But all clientdata and labels should be removed. */
int pNum;
Plane **cifplanes = (Plane **)def->cd_client;
UndoDisable();
/* cifplanes should be valid, but don't crash magic if not */
if (cifplanes != (Plane **)0)
for (pNum = 0; pNum < MAXCIFRLAYERS; pNum++)
{
for (pNum = 0; pNum < MAXCIFRLAYERS; pNum++)
if (cifplanes[pNum] != NULL)
{
if (cifplanes[pNum] != NULL)
{
DBFreePaintPlane(cifplanes[pNum]);
TiFreePlane(cifplanes[pNum]);
}
DBFreePaintPlane(cifplanes[pNum]);
TiFreePlane(cifplanes[pNum]);
}
freeMagic((char *)def->cd_client);
}
def->cd_client = (ClientData)0;
def->cd_flags &= ~CDFLATGDS;
freeMagic((char *)def->cd_client);
def->cd_client = (ClientData)CLIENTDEFAULT;
/* If the CDFLATTENED flag was not set, then this geometry */
/* was never instantiated, and should generate a warning. */
if (!(def->cd_flags & CDFLATTENED))
CIFReadError("%s read error: Unresolved geometry in cell"
" %s maps to no magic layers\n",
(type == 0) ? "CIF" : "GDS", def->cd_name);
#if 0
/* Remove the cell if it has no parents, no children, and no geometry */
/* To-do: Check that these conditions are valid */
if (def->cd_parents == (CellUse *)NULL)
{
char *savename = StrDup((char **)NULL, def->cd_name);
if (DBCellDeleteDef(def) == FALSE)
{
CIFReadError("%s read error: Unable to delete cell %s\n",
(type == 0) ? "CIF" : "GDS", savename);
}
else
{
if (type == 0)
TxPrintf("CIF read: Removed flattened cell %s\n", savename);
else
TxPrintf("GDS read: Removed flattened cell %s\n", savename);
}
freeMagic(savename);
}
#endif
UndoEnable();
}
}

View File

@ -3,25 +3,24 @@
* This file contains procedures that turn polygons into
* rectangles, as part of CIF file reading.
*
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
*/
#ifndef lint
static const char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magic-8.0/cif/CIFrdpoly.c,v 1.3 2010/06/24 12:37:15 tim Exp $";
static char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magic-8.0/cif/CIFrdpoly.c,v 1.3 2010/06/24 12:37:15 tim Exp $";
#endif /* not lint */
#include <stdio.h>
#include <stdlib.h> /* For qsort() */
#include "utils/magic.h"
#include "utils/geometry.h"
#include "tiles/tile.h"
@ -29,13 +28,12 @@ static const char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magi
#include "database/database.h"
#include "cif/CIFint.h"
#include "cif/CIFread.h"
#include "calma/calma.h"
#include "utils/malloc.h"
#define HEDGE 0 /* Horizontal edge */
#define REDGE 1 /* Rising edge */
#define FEDGE -1 /* Falling edge */
/*
* ----------------------------------------------------------------------------
*
@ -54,15 +52,11 @@ static const char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magi
* ----------------------------------------------------------------------------
*/
int
cifLowX(
const void *aa,
const void *bb)
int
cifLowX(a, b)
CIFPath **a, **b;
{
const CIFPath **a = (const CIFPath **)aa;
const CIFPath **b = (const CIFPath **)bb;
const Point *p, *q;
Point *p, *q;
p = &(*a)->cifp_point;
q = &(*b)->cifp_point;
@ -72,7 +66,7 @@ cifLowX(
return (1);
return (0);
}
/*
* ----------------------------------------------------------------------------
*
@ -91,20 +85,17 @@ cifLowX(
* ----------------------------------------------------------------------------
*/
int
cifLowY(
const void *aa,
const void *bb)
int
cifLowY(a, b)
Point **a, **b;
{
const Point **a = (const Point **)aa;
const Point **b = (const Point **)bb;
if ((*a)->p_y < (*b)->p_y)
return (-1);
if ((*a)->p_y > (*b)->p_y)
return (1);
return (0);
}
/*
* ----------------------------------------------------------------------------
*
@ -126,10 +117,10 @@ cifLowY(
*/
bool
cifOrient(
CIFPath *edges[], /* Array of edges to be categorized. */
int nedges, /* Size of arrays. */
int dir[]) /* Array to hold directions. */
cifOrient(edges, nedges, dir)
CIFPath *edges[]; /* Array of edges to be categorized. */
int dir[]; /* Array to hold directions. */
int nedges; /* Size of arrays. */
{
Point *p, *q;
int n;
@ -166,7 +157,7 @@ cifOrient(
}
return (TRUE);
}
/*
* ----------------------------------------------------------------------------
*
@ -186,11 +177,10 @@ cifOrient(
*/
bool
cifCross(
CIFPath *edge, /* Pointer to first of 2 path points in edge */
int dir, /* Direction of edge */
int ybot,
int ytop) /* Range of interest */
cifCross(edge, dir, ybot, ytop)
CIFPath *edge; /* Pointer to first of 2 path points in edge */
int dir; /* Direction of edge */
int ybot, ytop; /* Range of interest */
{
int ebot, etop;
@ -210,7 +200,7 @@ cifCross(
return (FALSE);
}
/*
* ----------------------------------------------------------------------------
*
@ -231,12 +221,11 @@ cifCross(
*/
LinkedRect *
CIFPolyToRects(
CIFPath *path, /* Path describing a polygon. */
Plane *plane, /* Plane to draw on */
const PaintResultType *resultTbl,
PaintUndoInfo *ui,
bool isCalma) /* TRUE for Calma, FALSE for CIF */
CIFPolyToRects(path, plane, resultTbl, ui)
CIFPath *path; /* Path describing a polygon. */
Plane *plane; /* Plane to draw on */
PaintResultType *resultTbl;
PaintUndoInfo *ui;
{
int npts = 0, n, *dir, curr, wrapno;
int xbot, xtop, ybot, ytop;
@ -250,9 +239,6 @@ CIFPolyToRects(
if ((tail->cifp_x != path->cifp_x) || (tail->cifp_y != path->cifp_y))
{
if (isCalma)
CalmaReadError("Boundary is not closed.\n" );
p = (CIFPath *) mallocMagic ((unsigned) sizeof (CIFPath));
p->cifp_x = path->cifp_x;
p->cifp_y = path->cifp_y;

View File

@ -4,21 +4,21 @@
* particular, it contains the routines to handle paint,
* including rectangles, wires, flashes, and polygons.
*
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
*/
#ifndef lint
static const char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magic-8.0/cif/CIFrdpt.c,v 1.2 2010/06/24 12:37:15 tim Exp $";
static char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magic-8.0/cif/CIFrdpt.c,v 1.2 2010/06/24 12:37:15 tim Exp $";
#endif /* not lint */
#include <stdio.h>
@ -37,9 +37,7 @@ static const char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magi
#include "cif/CIFint.h"
#include "cif/CIFread.h"
/* C99 compat */
#include "textio/textio.h"
/*
* ----------------------------------------------------------------------------
*
@ -65,13 +63,13 @@ static const char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magi
*/
bool
CIFParseBox(void)
CIFParseBox()
{
Point center;
Point direction;
Rect rectangle, r2;
int savescale;
/* Take the 'B'. */
TAKE();
@ -124,7 +122,7 @@ CIFParseBox(void)
rectangle.r_xbot = -rectangle.r_xtop;
rectangle.r_ybot = -rectangle.r_ytop;
/* Optional direction vector: have to build transform to do rotate. */
if (CIFParseSInteger(&direction.p_x))
@ -149,7 +147,7 @@ CIFParseBox(void)
DBPaintPlane(cifReadPlane, &r2, CIFPaintTable, (PaintUndoInfo *) NULL);
return TRUE;
}
/*
* ----------------------------------------------------------------------------
*
@ -176,13 +174,13 @@ CIFParseBox(void)
*/
bool
CIFParseFlash(void)
CIFParseFlash()
{
int diameter;
int savescale;
Point center;
Rect rectangle;
/* Take the 'R'. */
TAKE();
@ -236,13 +234,11 @@ CIFParseFlash(void)
*/
void
CIFPropRecordPath(
CellDef *def,
CIFPath *pathheadp,
bool iswire,
char *propname)
CIFPropRecordPath(def, pathheadp, iswire)
CellDef *def;
CIFPath *pathheadp;
{
extern float CIFGetOutputScale(int convert);
extern float CIFGetOutputScale();
CIFPath *pathp;
char *pathstr, *sptr;
int components;
@ -277,7 +273,7 @@ CIFPropRecordPath(
/* Reallocate pathstr to be no larger than needed to hold the path contents */
StrDup(&pathstr, pathstr);
DBPropPut(def, propname, (ClientData)pathstr);
DBPropPut(def, "path", (ClientData)pathstr);
}
/*
@ -316,13 +312,13 @@ CIFPropRecordPath(
*/
void
CIFPaintWirePath(
CIFPath *pathheadp,
int width,
bool endcap,
Plane *plane,
const PaintResultType *ptable,
PaintUndoInfo *ui)
CIFPaintWirePath(pathheadp, width, endcap, plane, ptable, ui)
CIFPath *pathheadp;
int width;
bool endcap;
Plane *plane;
PaintResultType *ptable;
PaintUndoInfo *ui;
{
CIFPath *pathp, *previousp, *nextp, *polypath;
CIFPath *returnpath, *newpath, *savepath;
@ -338,20 +334,18 @@ CIFPaintWirePath(
pathp = pathheadp->cifp_next;
if (pathp != NULL)
{
free_magic1_t mm1 = freeMagic1_init();
while (pathp->cifp_next != NULL)
{
if (pathp->cifp_next->cifp_x == pathp->cifp_x &&
pathp->cifp_next->cifp_y == pathp->cifp_y)
{
previousp->cifp_next = pathp->cifp_next;
freeMagic1(&mm1, pathp);
freeMagic(pathp);
}
else
previousp = pathp;
pathp = pathp->cifp_next;
}
freeMagic1_end(&mm1);
}
previousp = pathheadp;
@ -441,8 +435,7 @@ CIFPaintWirePath(
/* Wire reverses direction. Break wire here, */
/* draw, and start new polygon. */
TxError("Warning: direction reversal in path at (%d, %d).\n",
pathp->cifp_x, pathp->cifp_y);
TxError("Warning: direction reversal in path.\n");
phi = theta;
if (endcap)
@ -454,8 +447,7 @@ CIFPaintWirePath(
firstpoint = TRUE;
}
else {
TxError("Error: mitre limit exceeded at wire junction at (%d, %d).\n",
pathp->cifp_x, pathp->cifp_y);
TxError("Error: mitre limit exceeded at wire junction.\n");
TxError("Route has been truncated.\n");
break;
}
@ -485,16 +477,14 @@ CIFPaintWirePath(
/* Slow draw for non-Manhattan paths: */
/* Break the area up into triangles and rectangles */
rectp = CIFPolyToRects(polypath, plane, ptable, ui, FALSE);
rectp = CIFPolyToRects(polypath, plane, ptable, ui);
CIFFreePath(polypath);
free_magic1_t mm1 = freeMagic1_init();
for (; rectp != NULL ; rectp = rectp->r_next)
{
DBPaintPlane(plane, &rectp->r_r, ptable, ui);
freeMagic1(&mm1, (char *) rectp);
freeMagic((char *) rectp);
}
freeMagic1_end(&mm1);
polypath = NULL;
}
else
@ -568,18 +558,18 @@ CIFPaintWirePath(
*/
LinkedRect *
PaintPolygon(
Point *pointlist, /* Array of Point structures */
int number, /* total number of points */
Plane *plane, /* Plane structure to paint into */
PaintResultType *ptable, /* Paint result table */
PaintUndoInfo *ui, /* Undo record */
bool keep) /* Return list of rects if true */
PaintPolygon(pointlist, number, plane, ptable, ui, keep)
Point *pointlist; /* Array of Point structures */
int number; /* total number of points */
Plane *plane; /* Plane structure to paint into */
PaintResultType *ptable; /* Paint result table */
PaintUndoInfo *ui; /* Undo record */
bool keep; /* Return list of rects if true */
{
LinkedRect *rectp, *rectlist;
CIFPath *newpath, *cifpath = (CIFPath *)NULL;
int i;
for (i = 0; i < number; i++)
{
newpath = (CIFPath *) mallocMagic((unsigned) sizeof (CIFPath));
@ -589,16 +579,14 @@ PaintPolygon(
cifpath = newpath;
}
rectlist = CIFPolyToRects(cifpath, plane, ptable, ui, FALSE);
rectlist = CIFPolyToRects(cifpath, plane, ptable, ui);
CIFFreePath(cifpath);
free_magic1_t mm1 = freeMagic1_init();
for (rectp = rectlist; rectp != NULL ; rectp = rectp->r_next)
{
DBPaintPlane(plane, &rectp->r_r, ptable, ui);
if (!keep) freeMagic1(&mm1, (char *) rectp);
if (!keep) freeMagic((char *) rectp);
}
freeMagic1_end(&mm1);
return (keep) ? rectlist : (LinkedRect *)NULL;
}
@ -625,18 +613,18 @@ PaintPolygon(
*/
void
PaintWireList(
Point *pointlist, /* Array of Point structures */
int number, /* total number of points */
int width, /* Route width of path */
bool endcap, /* Whether or not to add 1/2 width endcaps */
Plane *plane, /* Plane structure to paint into */
PaintResultType *ptable, /* Paint result table */
PaintUndoInfo *ui) /* Undo record */
PaintWireList(pointlist, number, width, endcap, plane, ptable, ui)
Point *pointlist; /* Array of Point structures */
int number; /* total number of points */
int width; /* Route width of path */
bool endcap; /* Whether or not to add 1/2 width endcaps */
Plane *plane; /* Plane structure to paint into */
PaintResultType *ptable; /* Paint result table */
PaintUndoInfo *ui; /* Undo record */
{
CIFPath *newpath, *cifpath = (CIFPath *)NULL;
int i;
for (i = 0; i < number; i++)
{
newpath = (CIFPath *) mallocMagic((unsigned) sizeof (CIFPath));
@ -648,7 +636,7 @@ PaintWireList(
CIFPaintWirePath(cifpath, width, endcap, plane, ptable, ui);
}
/*
* ----------------------------------------------------------------------------
*
@ -669,7 +657,7 @@ PaintWireList(
*/
bool
CIFParseWire(void)
CIFParseWire()
{
int width;
CIFPath *pathheadp, *polypath;
@ -695,8 +683,7 @@ CIFParseWire(void)
width /= cifReadScale2;
savescale = cifReadScale1;
pathheadp = CIFParsePath(2);
if (pathheadp == NULL)
if (!CIFParsePath(&pathheadp, 2))
{
CIFReadError("wire, but improper path; ignored.\n");
CIFSkipToSemi();
@ -710,7 +697,7 @@ CIFParseWire(void)
return TRUE;
}
/*
* ----------------------------------------------------------------------------
*
@ -730,7 +717,7 @@ CIFParseWire(void)
*/
bool
CIFParseLayer(void)
CIFParseLayer()
{
#define MAXCHARS 4
char name[MAXCHARS+1];
@ -757,7 +744,7 @@ CIFParseLayer(void)
/* Set current plane for use by the routines that parse geometric
* elements.
*/
type = CIFReadNameToType(name, FALSE);
if (type < 0)
{
@ -773,7 +760,7 @@ CIFParseLayer(void)
CIFSkipToSemi();
return TRUE;
}
/*
* ----------------------------------------------------------------------------
*
@ -793,7 +780,7 @@ CIFParseLayer(void)
*/
bool
CIFParsePoly(void)
CIFParsePoly()
{
CIFPath *pathheadp;
LinkedRect *rectp;
@ -806,8 +793,7 @@ CIFParsePoly(void)
CIFSkipToSemi();
return FALSE;
}
pathheadp = CIFParsePath(1);
if (pathheadp == NULL)
if (!CIFParsePath(&pathheadp, 1))
{
CIFReadError("polygon, but improper path; ignored.\n");
CIFSkipToSemi();
@ -817,7 +803,7 @@ CIFParsePoly(void)
/* Convert the polygon to rectangles. */
rectp = CIFPolyToRects(pathheadp, cifReadPlane, CIFPaintTable,
(PaintUndoInfo *)NULL, FALSE);
(PaintUndoInfo *)NULL);
CIFFreePath(pathheadp);
if (rectp == NULL)
{
@ -827,13 +813,11 @@ CIFParsePoly(void)
CIFSkipToSemi();
return FALSE;
}
free_magic1_t mm1 = freeMagic1_init();
for (; rectp != NULL ; rectp = rectp->r_next)
{
DBPaintPlane(cifReadPlane, &rectp->r_r, CIFPaintTable,
(PaintUndoInfo *) NULL);
freeMagic1(&mm1, (char *) rectp);
freeMagic((char *) rectp);
}
freeMagic1_end(&mm1);
return TRUE;
}

View File

@ -4,21 +4,21 @@
* pertain to reading CIF files, and builds the tables used by
* the CIF-reading code.
*
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
*/
#ifndef lint
static const char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magic-8.0/cif/CIFrdtech.c,v 1.4 2010/09/15 15:45:30 tim Exp $";
static char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magic-8.0/cif/CIFrdtech.c,v 1.4 2010/09/15 15:45:30 tim Exp $";
#endif /* not lint */
#include <stdio.h>
@ -40,9 +40,6 @@ static const char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magi
#include "calma/calmaInt.h"
#include "utils/malloc.h"
/* C99 compat */
#include "cif/cif.h"
/* Pointer to a list of all the CIF-reading styles: */
CIFReadKeep *cifReadStyleList = NULL;
@ -62,8 +59,11 @@ CIFReadLayer *cifCurReadLayer; /* Current layer being processed. */
CIFOp *cifCurReadOp; /* Last geometric operation seen. */
/* Forward declarations */
void cifReadStyleInit(void);
void CIFReadLoadStyle(char *stylename);
void cifReadStyleInit();
void CIFReadLoadStyle();
/* Label types used by the "labels" statement option */
typedef enum { LABEL_TYPE_NONE, LABEL_TYPE_TEXT, LABEL_TYPE_PORT } labelType;
/*
* ----------------------------------------------------------------------------
@ -90,9 +90,8 @@ void CIFReadLoadStyle(char *stylename);
*/
bool
CIFReadTechLimitScale(
int ns,
int ds)
CIFReadTechLimitScale(ns, ds)
int ns, ds;
{
int gridup, scaledown;
int scale, limit, mult;
@ -132,9 +131,9 @@ CIFReadTechLimitScale(
*/
int
CIFReadNameToType(
char *name, /* Name of a CIF layer. */
bool newOK) /* TRUE means OK to create a new layer if this
CIFReadNameToType(name, newOK)
char *name; /* Name of a CIF layer. */
bool newOK; /* TRUE means OK to create a new layer if this
* name is one we haven't seen before.
*/
{
@ -146,7 +145,7 @@ CIFReadNameToType(
/* Only accept this layer if it's in the current CIF style or
* it's OK to add new layers to the current style.
*/
if (!TTMaskHasType(&cifCurReadStyle->crs_cifLayers, i) && !newOK)
continue;
if (strcmp(cifReadLayers[i], name) == 0)
@ -177,7 +176,7 @@ CIFReadNameToType(
cifNReadLayers += 1;
return cifNReadLayers-1;
}
/*
* ----------------------------------------------------------------------------
*
@ -197,40 +196,40 @@ CIFReadNameToType(
*/
int
CIFCalmaLayerToCifLayer(
int layer, /* Calma layer number */
int datatype, /* Calma datatype */
CIFReadStyle *calmaStyle)
CIFCalmaLayerToCifLayer(layer, datatype, calmaStyle)
int layer; /* Calma layer number */
int datatype; /* Calma datatype */
CIFReadStyle *calmaStyle;
{
CalmaLayerType clt;
HashEntry *he;
clt.clt_layer = layer;
clt.clt_type = datatype;
if ((he = HashLookOnly(&(calmaStyle->cifCalmaToCif), (char *) &clt)))
if (he = HashLookOnly(&(calmaStyle->cifCalmaToCif), (char *) &clt))
return ((spointertype) HashGetValue(he));
/* Try wildcarding the datatype */
clt.clt_type = -1;
if ((he = HashLookOnly(&(calmaStyle->cifCalmaToCif), (char *) &clt)))
if (he = HashLookOnly(&(calmaStyle->cifCalmaToCif), (char *) &clt))
return ((spointertype) HashGetValue(he));
/* Try wildcarding the layer */
clt.clt_layer = -1;
clt.clt_type = datatype;
if ((he = HashLookOnly(&(calmaStyle->cifCalmaToCif), (char *) &clt)))
if (he = HashLookOnly(&(calmaStyle->cifCalmaToCif), (char *) &clt))
return ((spointertype) HashGetValue(he));
/* Try wildcarding them both, for a default value */
clt.clt_layer = -1;
clt.clt_type = -1;
if ((he = HashLookOnly(&(calmaStyle->cifCalmaToCif), (char *) &clt)))
if (he = HashLookOnly(&(calmaStyle->cifCalmaToCif), (char *) &clt))
return ((spointertype) HashGetValue(he));
/* No luck */
return (-1);
}
/*
* ----------------------------------------------------------------------------
*
@ -252,10 +251,9 @@ CIFCalmaLayerToCifLayer(
*/
void
CIFParseReadLayers(
char *string, /* Comma-separated list of CIF layers. */
TileTypeBitMask *mask, /* Where to store bit mask. */
bool newok) /* If TRUE, create new layers if they don't exist */
CIFParseReadLayers(string, mask)
char *string; /* Comma-separated list of CIF layers. */
TileTypeBitMask *mask; /* Where to store bit mask. */
{
int i;
char *p;
@ -269,11 +267,11 @@ CIFParseReadLayers(
p = strchr(string, ',');
if (p != NULL)
*p = 0;
i = CIFReadNameToType(string, newok);
i = CIFReadNameToType(string, TRUE);
if (i >= 0)
TTMaskSetType(mask, i);
else if (newok)
else
{
HashEntry *he;
TileTypeBitMask *amask;
@ -285,15 +283,13 @@ CIFParseReadLayers(
TTMaskSetMask(mask, amask);
}
}
else
TxError("Error: CIF layer \"%s\" is unknown.\n", string);
if (p == NULL) break;
*p = ',';
for (string = p; *string == ','; string += 1) /* do nothing */;
}
}
/*
* ----------------------------------------------------------------------------
*
@ -314,7 +310,7 @@ CIFParseReadLayers(
*/
void
cifNewReadStyle(void)
cifNewReadStyle()
{
int i;
CIFOp *op;
@ -329,10 +325,8 @@ cifNewReadStyle(void)
layer = cifCurReadStyle->crs_layers[i];
if (layer != NULL)
{
free_magic1_t mm1 = freeMagic1_init();
for (op = layer->crl_ops; op != NULL; op = op->co_next)
freeMagic1(&mm1, (char *)op);
freeMagic1_end(&mm1);
freeMagic((char *)op);
freeMagic((char *)layer);
}
}
@ -356,7 +350,7 @@ cifNewReadStyle(void)
*/
void
cifReadStyleInit(void)
cifReadStyleInit()
{
int i;
@ -378,7 +372,7 @@ cifReadStyleInit(void)
cifCurReadStyle->crs_layers[i] = NULL;
}
}
/*
*
* ----------------------------------------------------------------------------
@ -398,25 +392,23 @@ cifReadStyleInit(void)
*/
void
CIFReadTechInit(void)
CIFReadTechInit()
{
CIFReadKeep *style;
/* Cleanup any old info. */
cifNewReadStyle();
freeMagic(cifCurReadStyle);
cifCurReadStyle = NULL;
/* forget the list of styles */
free_magic1_t mm1 = freeMagic1_init();
for (style = cifReadStyleList; style != NULL; style = style->crs_next)
{
{
freeMagic(style->crs_name);
freeMagic1(&mm1, style);
freeMagic(style);
}
freeMagic1_end(&mm1);
cifReadStyleList = NULL;
}
@ -438,14 +430,14 @@ CIFReadTechInit(void)
*/
void
CIFReadTechStyleInit(void)
CIFReadTechStyleInit()
{
cifNReadLayers = 0;
cifCurReadLayer = NULL;
cifCurReadOp = NULL;
}
/*
* ----------------------------------------------------------------------------
*
@ -465,10 +457,10 @@ CIFReadTechStyleInit(void)
*/
/* ARGSUSED */
bool
CIFReadTechLine(
char *sectionName, /* Name of this section ("cifinput"). */
int argc, /* Number of fields on line. */
char *argv[]) /* Values of fields. */
CIFReadTechLine(sectionName, argc, argv)
char *sectionName; /* Name of this section ("cifinput"). */
int argc; /* Number of fields on line. */
char *argv[]; /* Values of fields. */
{
CIFOp *newOp = NULL;
CIFReadKeep *newStyle, *p;
@ -485,7 +477,7 @@ CIFReadTechLine(
* make sure there's already a style around, and create one if
* there isn't.
*/
if (strcmp(argv[0], "style") == 0)
{
if (argc != 2)
@ -501,7 +493,7 @@ CIFReadTechLine(
return TRUE;
}
}
for (newStyle = cifReadStyleList; newStyle != NULL;
for (newStyle = cifReadStyleList; newStyle != NULL;
newStyle = newStyle->crs_next)
{
if (!strncmp(newStyle->crs_name, argv[1], l))
@ -555,7 +547,7 @@ CIFReadTechLine(
for (p = cifReadStyleList; p->crs_next; p = p->crs_next);
p->crs_next = newStyle;
}
if (cptr == NULL)
break;
else
@ -564,7 +556,7 @@ CIFReadTechLine(
newStyle = saveStyle;
}
}
if (cifCurReadStyle == NULL)
{
cifNewReadStyle();
@ -616,7 +608,7 @@ CIFReadTechLine(
if (cifCurReadStyle == NULL) return FALSE;
if ((cifCurReadStyle->crs_status != TECH_PENDING) &&
(cifCurReadStyle->crs_status != TECH_SUSPENDED)) return TRUE;
/* Process scalefactor lines next. */
if (strcmp(argv[0], "scalefactor") == 0)
@ -632,10 +624,8 @@ CIFReadTechLine(
if (argc >= 3)
{
if (!strncmp(argv[argc - 1], "nanom", 5))
if(!strncmp(argv[argc - 1], "nanom", 5))
cifCurReadStyle->crs_multiplier = 10;
else if (!strncmp(argv[argc - 1], "angstr", 6))
cifCurReadStyle->crs_multiplier = 100;
}
if (cifCurReadStyle->crs_scaleFactor <= 0)
@ -648,7 +638,7 @@ CIFReadTechLine(
}
/* Process "gridlimit" lines. */
if (strncmp(argv[0], "grid", 4) == 0)
{
if (StrIsInt(argv[1]))
@ -706,7 +696,7 @@ CIFReadTechLine(
return TRUE;
}
}
if (cptr == NULL)
break;
else
@ -748,13 +738,13 @@ CIFReadTechLine(
/* Handle a special case of a list of layer names on the
* layer line. Turn them into an OR operation.
*/
if (argc == 3)
{
cifCurReadOp = (CIFOp *) mallocMagic(sizeof(CIFOp));
cifCurReadOp->co_opcode = CIFOP_OR;
cifCurReadOp->co_client = (ClientData)NULL;
CIFParseReadLayers(argv[2], &cifCurReadOp->co_cifMask, TRUE);
CIFParseReadLayers(argv[2], &cifCurReadOp->co_cifMask);
TTMaskZero(&cifCurReadOp->co_paintMask);
cifCurReadOp->co_next = NULL;
cifCurReadOp->co_distance = 0;
@ -798,13 +788,13 @@ CIFReadTechLine(
/* Handle a special case of a list of layer names on the
* layer line. Turn them into an OR operation.
*/
if (argc == 3)
{
cifCurReadOp = (CIFOp *) mallocMagic(sizeof(CIFOp));
cifCurReadOp->co_opcode = CIFOP_OR;
cifCurReadOp->co_client = (ClientData)NULL;
CIFParseReadLayers(argv[2], &cifCurReadOp->co_cifMask, TRUE);
CIFParseReadLayers(argv[2], &cifCurReadOp->co_cifMask);
TTMaskZero(&cifCurReadOp->co_paintMask);
cifCurReadOp->co_next = NULL;
cifCurReadOp->co_distance = 0;
@ -847,7 +837,7 @@ CIFReadTechLine(
/* Figure out which Magic layer should get labels from which
* CIF layers.
*/
if (strcmp(argv[0], "labels") == 0)
{
TileTypeBitMask mask;
@ -868,42 +858,17 @@ CIFReadTechLine(
calmaLabelType = LABEL_TYPE_TEXT;
else if (!strcmp(argv[2], "port"))
calmaLabelType = LABEL_TYPE_PORT;
else if (!strncmp(argv[2], "cell", 4))
calmaLabelType = LABEL_TYPE_CELLID;
else
goto wrongNumArgs;
}
else
goto wrongNumArgs;
}
CIFParseReadLayers(argv[1], &mask, TRUE);
for (i = 0; i < MAXCIFRLAYERS; i++)
CIFParseReadLayers(argv[1], &mask);
for (i=0; i<MAXCIFRLAYERS; i+=1)
{
if (TTMaskHasType(&mask, i))
if (TTMaskHasType(&mask,i))
{
/* Only one magic type can be assigned to a GDS layer, so
* multiple assignments should be flagged as errors. BUT,
* this is a common historic error. Since reattachments
* should be handled rationally (by code added 10/17/2023
* to DBlabel.c), there is no urgent need to flag an issue
* unless the new layer does not exist on the same plane
* as the old one.
*/
if (cifCurReadStyle->crs_labelLayer[i] != TT_SPACE)
{
int p1, p2;
p1 = DBPlane(cifCurReadLayer->crl_magicType);
p2 = DBPlane(cifCurReadStyle->crs_labelLayer[i]);
if (!DBTypeOnPlane(cifCurReadLayer->crl_magicType, p2) &&
!DBTypeOnPlane(cifCurReadStyle->crs_labelLayer[i], p1))
TechError("Labels on layer \"%s\" attached to \"%s\" "
"supersedes prior attachment to \"%s\".\n",
cifReadLayers[i],
DBTypeLongNameTbl[cifCurReadLayer->crl_magicType],
DBTypeLongNameTbl[cifCurReadStyle->crs_labelLayer[i]]);
}
cifCurReadStyle->crs_labelLayer[i]
= cifCurReadLayer->crl_magicType;
if (argc == 3)
@ -918,17 +883,17 @@ CIFReadTechLine(
* will cause the layers to be ignored when encountered in
* cells.
*/
if (strcmp(argv[0], "ignore") == 0)
{
TileTypeBitMask mask;
int i;
if (argc != 2) goto wrongNumArgs;
CIFParseReadLayers(argv[1], &mask, TRUE);
CIFParseReadLayers(argv[1], &mask);
/* trash the value in crs_labelLayer so that any labels on this
* layer get junked, also. dcs 4/11/90
*/
layer get junked, also. dcs 4/11/90
*/
for (i=0; i < cifNReadLayers; i++)
{
if (TTMaskHasType(&mask,i))
@ -944,23 +909,22 @@ CIFReadTechLine(
/* miscellaneous cif-reading boolean options */
if (strcmp(argv[0], "options") == 0) {
if(strcmp(argv[0], "options") == 0) {
int i;
if (argc < 2) goto wrongNumArgs;
for (i = 1; i < argc; i++) {
if (strcmp(argv[i], "ignore-unknown-layer-labels") == 0)
for(i = 1; i < argc; i++) {
if(strcmp(argv[i], "ignore-unknown-layer-labels") == 0)
cifCurReadStyle->crs_flags |= CRF_IGNORE_UNKNOWNLAYER_LABELS;
/* Allow "no-reconnect-labels", although it has been deprecated */
else if (strcmp(argv[i], "no-reconnect-labels") != 0)
TechError("Unknown cifinput option \"%s\".\n", argv[i]);
if(strcmp(argv[i], "no-reconnect-labels") == 0)
cifCurReadStyle->crs_flags |= CRF_NO_RECONNECT_LABELS;
}
return TRUE;
}
/* Anything below here is a geometric operation, so we can
* do some set-up that is common to all the operations.
*/
if (cifCurReadLayer == NULL)
{
TechError("Must define layer before specifying operations.\n");
@ -988,8 +952,6 @@ CIFReadTechLine(
newOp->co_opcode = CIFOP_SHRINK;
else if (strcmp(argv[0], "copyup") == 0)
newOp->co_opcode = CIFOP_COPYUP;
else if (strcmp(argv[0], "boundary") == 0)
newOp->co_opcode = CIFOP_BOUNDARY;
else
{
TechError("Unknown statement \"%s\".\n", argv[0]);
@ -1003,8 +965,9 @@ CIFReadTechLine(
case CIFOP_OR:
case CIFOP_COPYUP:
if (argc != 2) goto wrongNumArgs;
CIFParseReadLayers(argv[1], &newOp->co_cifMask, TRUE);
CIFParseReadLayers(argv[1], &newOp->co_cifMask);
break;
case CIFOP_GROW:
case CIFOP_GROW_G:
case CIFOP_SHRINK:
@ -1036,7 +999,7 @@ CIFReadTechLine(
return TRUE;
}
/*
* ----------------------------------------------------------------------------
*
@ -1056,7 +1019,7 @@ CIFReadTechLine(
*/
void
CIFReadTechFinal(void)
CIFReadTechFinal()
{
/* Reduce the scale by the multiplier, as much as possible while */
/* keeping all CIF input ops in integer units. */
@ -1100,8 +1063,8 @@ CIFReadTechFinal(void)
* ----------------------------------------------------------------------------
*/
void
CIFReadLoadStyle(
char *stylename)
CIFReadLoadStyle(stylename)
char *stylename;
{
SectionID invcifr;
@ -1116,7 +1079,7 @@ CIFReadLoadStyle(
/* CIFReadTechFinal(); */ /* Taken care of by TechLoad() */
CIFTechInputScale(DBLambda[0], DBLambda[1], TRUE);
}
/*
* ----------------------------------------------------------------------------
*
@ -1143,8 +1106,8 @@ CIFReadLoadStyle(
*/
int
CIFReadGetGrowSize(
TileType type)
CIFReadGetGrowSize(type)
TileType type;
{
CIFReadStyle *istyle = cifCurReadStyle;
CIFOp *op;
@ -1198,8 +1161,8 @@ CIFReadGetGrowSize(
*/
float
CIFGetInputScale(
int convert)
CIFGetInputScale(convert)
int convert;
{
/* Avoid divide-by-0 error if there is no cif input style */
/* in the tech file. */
@ -1231,10 +1194,10 @@ CIFGetInputScale(
*/
void
CIFPrintReadStyle(
bool dolist, /* Return as a list if true */
bool doforall, /* Return list of all styles if true */
bool docurrent) /* Return current style if true */
CIFPrintReadStyle(dolist, doforall, docurrent)
bool dolist; /* Return as a list if true */
bool doforall; /* Return list of all styles if true */
bool docurrent; /* Return current style if true */
{
CIFReadKeep *style;
@ -1281,7 +1244,7 @@ CIFPrintReadStyle(
}
}
/*
* ----------------------------------------------------------------------------
*
@ -1302,8 +1265,8 @@ CIFPrintReadStyle(
*/
void
CIFSetReadStyle(
char *name) /* Name of the new style. If NULL,
CIFSetReadStyle(name)
char *name; /* Name of the new style. If NULL,
* just print the name of the current
* style.
*/
@ -1339,7 +1302,7 @@ CIFSetReadStyle(
TxError("\"%s\" is not one of the CIF input styles Magic knows.\n", name);
CIFPrintReadStyle(FALSE, TRUE, TRUE);
}
/*
* ----------------------------------------------------------------------------
*
@ -1363,10 +1326,10 @@ CIFSetReadStyle(
*/
int
cifParseCalmaNums(
char *str, /* String to parse */
int *numArray, /* Array to fill in */
int numNums) /* Maximum number of entries in numArray */
cifParseCalmaNums(str, numArray, numNums)
char *str; /* String to parse */
int *numArray; /* Array to fill in */
int numNums; /* Maximum number of entries in numArray */
{
int numFilled, num;
@ -1426,10 +1389,9 @@ cifParseCalmaNums(
*/
int
CIFTechInputScale(
int n,
int d,
bool opt)
CIFTechInputScale(n, d, opt)
int n, d;
bool opt;
{
CIFReadStyle *istyle = cifCurReadStyle;
CIFReadLayer *cl;

View File

@ -5,21 +5,21 @@
* reading CIF files, plus a bunch of utility routines
* for skipping white space, parsing numbers and points, etc.
*
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
*/
#ifndef lint
static const char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magic-8.0/cif/CIFrdutils.c,v 1.4 2010/06/24 12:37:15 tim Exp $";
static char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magic-8.0/cif/CIFrdutils.c,v 1.4 2010/06/24 12:37:15 tim Exp $";
#endif /* not lint */
#include <stdio.h>
@ -27,12 +27,6 @@ static const char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magi
#include <stdarg.h>
#include <ctype.h>
/*
* C99 compat
* Mind: tcltk/tclmagic.h must be included prior to all the other headers
*/
#include "tcltk/tclmagic.h"
#include "utils/magic.h"
#include "utils/geometry.h"
#include "tiles/tile.h"
@ -46,16 +40,6 @@ static const char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magi
#include "utils/undo.h"
#include "utils/malloc.h"
/* C99 compat */
#include "lef/lef.h"
#include "drc/drc.h"
#include "extract/extract.h"
#include "wiring/wiring.h"
#include "router/router.h"
#include "mzrouter/mzrouter.h"
#include "irouter/irouter.h"
#include "plow/plow.h"
/* The following variables are used to provide one character of
* lookahead. cifParseLaAvail is TRUE if cifParseLaChar contains
* a valid character, FALSE otherwise. The PEEK and TAKE macros
@ -76,7 +60,6 @@ FILE *cifErrorFile;
int cifLineNumber; /* Number of current line. */
int cifTotalWarnings; /* Number of warnings detected */
int cifTotalErrors; /* Number of errors detected */
bool cifSeenSnapWarning; /* Track this to prevent excessive messaging */
/* The variables used below hold general information about what
* we're currently working on.
@ -109,7 +92,7 @@ Plane *cifReadPlane; /* Plane into which to paint material
* NULL means no layer command has
* been seen for the current cell.
*/
/*
* ----------------------------------------------------------------------------
*
@ -129,7 +112,7 @@ Plane *cifReadPlane; /* Plane into which to paint material
/* VARARGS1 */
void
CIFReadError(const char *format, ...)
CIFReadError(char *format, ...)
{
va_list args;
@ -137,10 +120,7 @@ CIFReadError(const char *format, ...)
if (CIFWarningLevel == CIF_WARN_NONE) return;
if ((cifTotalErrors < 100) || (CIFWarningLevel != CIF_WARN_LIMIT))
{
if (cifLineNumber > 0)
TxError("Error at line %d of CIF file: ", cifLineNumber);
else
TxError("CIF file read error: ");
TxError("Error at line %d of CIF file: ", cifLineNumber);
va_start(args, format);
Vfprintf(stderr, format, args);
va_end(args);
@ -150,10 +130,10 @@ CIFReadError(const char *format, ...)
TxError("Error limit set: Remaining errors will not be reported.\n");
}
}
void
CIFReadWarning(const char *format, ...)
CIFReadWarning(char *format, ...)
{
va_list args;
@ -161,10 +141,7 @@ CIFReadWarning(const char *format, ...)
if (CIFWarningLevel == CIF_WARN_NONE) return;
if ((cifTotalWarnings < 100) || (CIFWarningLevel != CIF_WARN_LIMIT))
{
if (cifLineNumber > 0)
TxError("Warning at line %d of CIF file: ", cifLineNumber);
else
TxError("CIF file read warning: ");
TxError("Warning at line %d of CIF file: ", cifLineNumber);
va_start(args, format);
Vfprintf(stderr, format, args);
va_end(args);
@ -205,9 +182,9 @@ CIFReadWarning(const char *format, ...)
*/
int
CIFScaleCoord(
int cifCoord, /* A coordinate in CIF units. */
int snap_type) /* How to deal with fractional results */
CIFScaleCoord(cifCoord, snap_type)
int cifCoord; /* A coordinate in CIF units. */
int snap_type; /* How to deal with fractional results */
{
int result, scale, remain, denom;
int mult, mfactor;
@ -235,10 +212,8 @@ CIFScaleCoord(
switch (snap_type)
{
case COORD_EXACT:
if (!cifSeenSnapWarning)
CIFReadWarning("Input off lambda grid by %d/%d; grid redefined.\n",
CIFReadWarning("Input off lambda grid by %d/%d; grid redefined.\n",
remain, denom);
cifSeenSnapWarning = TRUE;
CIFTechInputScale(1, denom, FALSE);
CIFTechOutputScale(1, denom);
@ -262,10 +237,8 @@ CIFScaleCoord(
case COORD_HALF_U: case COORD_HALF_L:
if (denom > 2)
{
if (!cifSeenSnapWarning)
CIFReadWarning("Input off lambda grid by %d/%d; "
"grid redefined.\n", remain, denom);
cifSeenSnapWarning = TRUE;
CIFReadWarning("Input off lambda grid by %d/%d; grid redefined.\n",
remain, denom);
/* scale to nearest half-lambda */
if (!(denom & 0x1)) denom >>= 1;
@ -276,10 +249,8 @@ CIFScaleCoord(
PlowAfterTech();
ExtTechScale(1, denom);
WireTechScale(1, denom);
#ifdef ROUTE_MODULE
MZAfterTech();
IRAfterTech();
#endif
#ifdef LEF_MODULE
LefTechScale(1, denom);
#endif
@ -300,10 +271,8 @@ CIFScaleCoord(
break;
case COORD_ANY:
if (!cifSeenSnapWarning)
CIFReadWarning("Input off lambda grid by %d/%d; snapped to grid.\n",
abs(remain), abs(denom));
cifSeenSnapWarning = TRUE;
CIFReadWarning("Input off lambda grid by %d/%d; snapped to grid.\n",
abs(remain), abs(denom));
/* Careful: must round down a bit more for negative numbers, in
* order to ensure that a point exactly halfway between Magic units
@ -325,7 +294,7 @@ CIFScaleCoord(
return result;
}
/*
* ----------------------------------------------------------------------------
*
@ -345,8 +314,8 @@ CIFScaleCoord(
*/
bool
cifIsBlank(
int ch)
cifIsBlank(ch)
int ch;
{
if ( isdigit(ch) || isupper(ch)
@ -358,7 +327,7 @@ cifIsBlank(
}
else return TRUE;
}
/*
* ----------------------------------------------------------------------------
*
@ -378,9 +347,9 @@ cifIsBlank(
*/
void
CIFSkipBlanks(void)
CIFSkipBlanks()
{
while (cifIsBlank(PEEK())) {
if (TAKE() == '\n')
{
@ -388,7 +357,7 @@ CIFSkipBlanks(void)
}
}
}
/*
* ----------------------------------------------------------------------------
*
@ -407,7 +376,7 @@ CIFSkipBlanks(void)
*/
void
CIFSkipSep(void)
CIFSkipSep()
{
int ch;
@ -418,7 +387,7 @@ CIFSkipSep(void)
}
}
}
/*
* ----------------------------------------------------------------------------
*
@ -437,10 +406,10 @@ CIFSkipSep(void)
*/
void
CIFSkipToSemi(void)
CIFSkipToSemi()
{
int ch;
for (ch = PEEK() ; ((ch != ';') && (ch != EOF)) ; ch = PEEK()) {
if (TAKE() == '\n')
{
@ -448,7 +417,7 @@ CIFSkipToSemi(void)
}
}
}
/*
* ----------------------------------------------------------------------------
*
@ -466,9 +435,9 @@ CIFSkipToSemi(void)
*/
void
CIFSkipSemi(void)
CIFSkipSemi()
{
CIFSkipBlanks();
if (PEEK() != ';') {
CIFReadError("`;\' expected.\n");
@ -477,7 +446,7 @@ CIFSkipSemi(void)
TAKE();
CIFSkipBlanks();
}
/*
* ----------------------------------------------------------------------------
*
@ -497,8 +466,8 @@ CIFSkipSemi(void)
*/
bool
CIFParseSInteger(
int *valuep)
CIFParseSInteger(valuep)
int *valuep;
{
bool is_signed;
char buffer[ BUFSIZ ];
@ -523,7 +492,7 @@ CIFParseSInteger(
*valuep = -(*valuep);
return TRUE;
}
/*
* ----------------------------------------------------------------------------
*
@ -542,8 +511,8 @@ CIFParseSInteger(
*/
bool
CIFParseInteger(
int *valuep)
CIFParseInteger(valuep)
int *valuep;
{
if (!CIFParseSInteger(valuep))
@ -583,9 +552,9 @@ CIFParseInteger(
*/
bool
CIFParsePoint(
Point *pointp,
int iscale)
CIFParsePoint(pointp, iscale)
Point *pointp;
int iscale;
{
int rescale;
@ -641,7 +610,7 @@ CIFParsePoint(
return TRUE;
}
/*
* ----------------------------------------------------------------------------
*
@ -651,11 +620,12 @@ CIFParsePoint(
* one or more points.
*
* Results:
* non-NULL CIFPath* the caller takes ownership of
* if the path was parsed successfully, otherwise NULL.
* TRUE is returned if the path was parsed successfully,
* FALSE otherwise.
*
* Side effects:
* None
* Modifies the parameter pathheadpp to point to the path
* that is constructed.
*
* Corrections:
* CIF coordinates are multiplied by 2 to cover the case where
@ -667,16 +637,17 @@ CIFParsePoint(
* ----------------------------------------------------------------------------
*/
CIFPath *
CIFParsePath(
int iscale)
bool
CIFParsePath(pathheadpp, iscale)
CIFPath **pathheadpp;
int iscale;
{
CIFPath *pathheadp, *pathtailp, *newpathp;
CIFPath *pathtailp, *newpathp;
bool nonManhattan = FALSE; /* diagnostic only */
CIFPath path;
int savescale;
pathheadp = NULL;
*pathheadpp = NULL;
pathtailp = NULL;
path.cifp_next = NULL;
while (TRUE)
@ -688,12 +659,12 @@ CIFParsePath(
savescale = cifReadScale1;
if (!CIFParsePoint(&path.cifp_point, iscale))
{
CIFFreePath(pathheadp);
return NULL;
CIFFreePath(*pathheadpp);
return FALSE;
}
if (savescale != cifReadScale1)
{
CIFPath *phead = pathheadp;
CIFPath *phead = *pathheadpp;
int newscale = cifReadScale1 / savescale;
while (phead != NULL)
{
@ -704,7 +675,7 @@ CIFParsePath(
}
newpathp = (CIFPath *) mallocMagic((unsigned) (sizeof (CIFPath)));
*newpathp = path;
if (pathheadp)
if (*pathheadpp)
{
/*
* Check that this segment is Manhattan. If not, remember the
@ -721,10 +692,10 @@ CIFParsePath(
}
pathtailp->cifp_next = newpathp;
}
else pathheadp = newpathp;
else *pathheadpp = newpathp;
pathtailp = newpathp;
}
return pathheadp;
return (*pathheadpp != NULL);
}
/*
@ -736,7 +707,7 @@ CIFParsePath(
* first three points in the given CIF path.
*
* Results:
* TRUE if point is inside, FALSE if outside or on the border
* TRUE if point is inside, FALSE if outside or on the border
*
* Side effects:
* None.
@ -744,9 +715,9 @@ CIFParsePath(
*/
bool
test_insideness(
CIFPath *start,
Point *tpoint)
test_insideness(start, tpoint)
CIFPath *start;
Point *tpoint;
{
Rect tmprect, irect;
@ -777,16 +748,15 @@ test_insideness(
* Side effects:
* value of respt contains point to which segment will be
* truncated.
*
*
* ----------------------------------------------------------------------------
*/
bool
seg_intersect(
CIFPath *tstart,
Point *bf,
Point *bs,
Point *respt)
seg_intersect(tstart, bf, bs, respt)
CIFPath *tstart;
Point *bf, *bs;
Point *respt;
{
int afx = tstart->cifp_x;
int afy = tstart->cifp_y;
@ -849,10 +819,9 @@ seg_intersect(
*/
bool
path_intersect(
CIFPath *pathHead,
CIFPath *start,
Point *respt)
path_intersect(pathHead, start, respt)
CIFPath *pathHead, *start;
Point *respt;
{
CIFPath *path, *segcrossed, *new;
Point tmppt;
@ -881,7 +850,7 @@ path_intersect(
/* with the smaller absolute distance takes precedence.) */
if (test_insideness(start, &path->cifp_point)) {
int tmpdist = abs(newdist); /* save this value */
int tmpdist = abs(newdist); /* save this value */
if (path->cifp_x == path->cifp_next->cifp_x ||
path->cifp_y == path->cifp_next->cifp_y)
{
@ -955,8 +924,8 @@ path_intersect(
*/
bool
is_clockwise(
CIFPath *pathHead)
is_clockwise(pathHead)
CIFPath *pathHead;
{
CIFPath *path, *midx = NULL, *last;
Point *p1, *p2, *p3;
@ -1049,11 +1018,11 @@ is_clockwise(
*/
void
CIFMakeManhattanPath(
CIFPath *pathHead,
Plane *plane,
const PaintResultType *resultTbl,
PaintUndoInfo *ui)
CIFMakeManhattanPath(pathHead, plane, resultTbl, ui)
CIFPath *pathHead;
Plane *plane;
PaintResultType *resultTbl;
PaintUndoInfo *ui;
{
CIFPath *new, *new2, *next, *path;
int xinit, xdiff, xincr, xlast, x;
@ -1097,7 +1066,7 @@ CIFMakeManhattanPath(
edir = CIFEdgeDirection(first, last);
if (edir == CIF_DIAG_DL || edir == CIF_DIAG_UR)
{
new->cifp_x = first->cifp_x;
new->cifp_x = first->cifp_x;
new->cifp_y = last->cifp_y;
}
else /* edir == CIF_DIAG_DR || edir == CIF_DIAG_UL */
@ -1156,15 +1125,11 @@ CIFMakeManhattanPath(
/* Final check---ensure that rectangle is not degenerate */
if (plane && (tr.r_xtop - tr.r_xbot > 0) && (tr.r_ytop - tr.r_ybot > 0))
{
DBNMPaintPlane(plane, type, &tr, resultTbl, ui);
GEO_EXPAND(&tr, 1, &tr);
DBMergeNMTiles(plane, &tr, ui);
}
}
}
/*
* ----------------------------------------------------------------------------
*
@ -1187,9 +1152,8 @@ CIFMakeManhattanPath(
*/
int
CIFEdgeDirection(
CIFPath *first,
CIFPath *last) /* Edge to be categorized. */
CIFEdgeDirection(first, last)
CIFPath *first, *last; /* Edge to be categorized. */
{
if (first->cifp_x < last->cifp_x)
@ -1214,7 +1178,7 @@ CIFEdgeDirection(
return CIF_DOWN;
return CIF_ZERO;
}
/*
* ----------------------------------------------------------------------------
*
@ -1236,8 +1200,8 @@ CIFEdgeDirection(
*/
void
CIFCleanPath(
CIFPath *pathHead)
CIFCleanPath(pathHead)
CIFPath *pathHead;
{
CIFPath *next, *path, *prev, *last;
int dir1, dir2;
@ -1255,8 +1219,8 @@ CIFCleanPath(
path = next;
if (!path) return;
}
while ((next = path->cifp_next))
while (next = path->cifp_next)
{
if ((dir2 = CIFEdgeDirection(path, next)) == CIF_ZERO)
{
@ -1289,7 +1253,7 @@ path_inc:
if (!pathHead->cifp_next)
{
/* Ensure that the resulting path is closed. */
if ((pathHead->cifp_x != path->cifp_x) ||
if ((pathHead->cifp_x != path->cifp_x) ||
(pathHead->cifp_y != path->cifp_y))
{
next = (CIFPath *) mallocMagic((unsigned) (sizeof (CIFPath)));
@ -1317,7 +1281,7 @@ path_inc:
}
}
}
/*
* ----------------------------------------------------------------------------
*
@ -1335,18 +1299,16 @@ path_inc:
*/
void
CIFFreePath(
CIFPath *path) /* Path to be freed. */
CIFFreePath(path)
CIFPath *path; /* Path to be freed. */
{
free_magic1_t mm1 = freeMagic1_init();
while (path != NULL)
{
freeMagic1(&mm1, (char *) path);
freeMagic((char *) path);
path = path->cifp_next;
}
freeMagic1_end(&mm1);
}
/*
* ----------------------------------------------------------------------------
*
@ -1366,13 +1328,13 @@ CIFFreePath(
*/
void
cifCommandError(void)
cifCommandError()
{
CIFReadError("unknown command `%c'; ignored.\n" , PEEK());
CIFSkipToSemi();
}
/*
* ----------------------------------------------------------------------------
*
@ -1391,7 +1353,7 @@ cifCommandError(void)
*/
bool
cifParseEnd(void)
cifParseEnd()
{
TAKE();
CIFSkipBlanks();
@ -1402,7 +1364,7 @@ cifParseEnd(void)
}
return TRUE;
}
/*
* ----------------------------------------------------------------------------
*
@ -1420,11 +1382,11 @@ cifParseEnd(void)
*/
bool
cifParseComment(void)
cifParseComment()
{
int opens;
int ch;
/*
* take the '('
*/
@ -1449,7 +1411,7 @@ cifParseComment(void)
} while (opens > 0);
return TRUE;
}
/*
* ----------------------------------------------------------------------------
*
@ -1471,9 +1433,9 @@ cifParseComment(void)
* ----------------------------------------------------------------------------
*/
const Transform *
CIFDirectionToTrans(
const Point *point) /* Direction vector from origin. */
Transform *
CIFDirectionToTrans(point)
Point *point; /* Direction vector from origin. */
{
if ((point->p_x != 0) && (point->p_y == 0))
{
@ -1491,7 +1453,7 @@ CIFDirectionToTrans(
point->p_x, point->p_y);
return &GeoIdentityTransform;
}
/*
* ----------------------------------------------------------------------------
*
@ -1512,8 +1474,8 @@ CIFDirectionToTrans(
*/
bool
CIFParseTransform(
Transform *transformp)
CIFParseTransform(transformp)
Transform *transformp;
{
char ch;
Point point;
@ -1586,7 +1548,7 @@ CIFParseTransform(
return TRUE;
}
/*
* ----------------------------------------------------------------------------
*
@ -1606,8 +1568,8 @@ CIFParseTransform(
*/
void
CIFReadFile(
FILE *file) /* File from which to read CIF. */
CIFReadFile(file)
FILE *file; /* File from which to read CIF. */
{
/* We will use 1-word CIF numbers as keys in this hash table */
CIFReadCellInit(1);
@ -1623,7 +1585,6 @@ CIFReadFile(
cifTotalWarnings = 0;
cifTotalErrors = 0;
CifPolygonCount = 0;
cifSeenSnapWarning = FALSE;
cifInputFile = file;
cifReadScale1 = 1;
@ -1699,6 +1660,6 @@ CIFReadFile(
CIFReadError("no \"End\" statement.\n");
done:
CIFReadCellCleanup(FILE_CIF);
CIFReadCellCleanup(0);
UndoEnable();
}

View File

@ -5,24 +5,24 @@
* by the CIF writing code. The definitions are only used internally
* to this module.
*
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
*
*
* rcsid "$Header: /usr/cvsroot/magic-8.0/cif/CIFread.h,v 1.3 2010/08/25 17:33:55 tim Exp $
*/
#ifndef _MAGIC__CIF__CIFREAD_H
#define _MAGIC__CIF__CIFREAD_H
#ifndef _CIFREAD_H
#define _CIFREAD_H
#include "cif/CIFint.h"
@ -54,8 +54,8 @@ typedef struct
* the "crl_magicType" should be interpreted as a CIF layer.
*/
#define CIFR_SIMPLE 1
#define CIFR_TEMPLAYER 2
#define CIFR_SIMPLE 1
#define CIFR_TEMPLAYER 2
/* The following structure defines a complete CIF read-in style.
* The constant MAXCIFRLAYERS must be less than TT_MAXTYPES, and
@ -104,10 +104,8 @@ typedef struct cifrstyle
/* Gives the Magic layer to use for labels
* on each possible CIF layer.
*/
/* enum labelType */ unsigned char crs_labelSticky[MAXCIFRLAYERS];
/* Marker if label layer makes sticky labels
* enum labelType LABEL_TYPE_xxxxxx
*/
bool crs_labelSticky[MAXCIFRLAYERS];
/* Marker if label layer makes sticky labels */
CIFReadLayer *crs_layers[MAXCIFRLAYERS];
HashTable cifCalmaToCif; /* Table mapping from Calma layer numbers to
* CIF layers
@ -117,6 +115,7 @@ typedef struct cifrstyle
/* option bitmasks used in crs_flags */
#define CRF_IGNORE_UNKNOWNLAYER_LABELS 1
#define CRF_NO_RECONNECT_LABELS 2
/* Methods to deal with fractional results of conversion from CIF to magic */
/* units (see routine CIFScaleCoord() for details). */
@ -154,45 +153,22 @@ typedef struct cifpath
/* Procedures */
extern bool CIFParseBox(void);
extern bool CIFParseWire(void);
extern bool CIFParsePoly(void);
extern bool CIFParseFlash(void);
extern bool CIFParseLayer(void);
extern bool CIFParseStart(void);
extern bool CIFParseFinish(void);
extern bool CIFParseDelete(void);
extern bool CIFParseUser(void);
extern bool CIFParseCall(void);
extern bool CIFParseTransform(Transform *transformp);
extern bool CIFParseInteger(int *valuep);
extern CIFPath *CIFParsePath(int iscale);
extern bool CIFParsePoint(Point *pointp, int iscale);
extern bool CIFParseSInteger(int *valuep);
extern void CIFSkipToSemi(void);
extern void CIFSkipSep(void);
extern void CIFSkipBlanks(void);
extern void CIFFreePath(CIFPath *path);
extern void CIFCleanPath(CIFPath *pathHead);
extern void CIFReadCellInit(int ptrkeys);
extern void CIFReadCellCleanup(int filetype);
extern LinkedRect *CIFPolyToRects(CIFPath *path, Plane *plane, const PaintResultType *resultTbl,
PaintUndoInfo *ui, bool isCalma);
extern const Transform *CIFDirectionToTrans(const Point *point);
extern int CIFReadNameToType(char *name, bool newOK);
extern int CIFCalmaLayerToCifLayer(int layer, int datatype, CIFReadStyle *calmaStyle);
extern void CIFPropRecordPath(CellDef *def, CIFPath *pathheadp, bool iswire, char *propname);
extern void CIFPaintWirePath(CIFPath *pathheadp, int width, bool endcap, Plane *plane,
const PaintResultType *ptable, PaintUndoInfo *ui);
extern void CIFMakeManhattanPath(CIFPath *pathHead, Plane *plane, const PaintResultType *resultTbl, PaintUndoInfo *ui);
extern int CIFEdgeDirection(CIFPath *first, CIFPath *last);
extern bool CIFParseBox(), CIFParseWire(), CIFParsePoly();
extern bool CIFParseFlash(), CIFParseLayer(), CIFParseStart();
extern bool CIFParseFinish(), CIFParseDelete(), CIFParseUser();
extern bool CIFParseCall(), CIFParseTransform(), CIFParseInteger();
extern bool CIFParsePath(), CIFParsePoint(), CIFParseSInteger();
extern void CIFSkipToSemi(), CIFSkipSep(), CIFSkipBlanks();
extern void CIFFreePath(), CIFCleanPath();
extern void CIFReadCellInit(), CIFReadCellCleanup();
extern LinkedRect *CIFPolyToRects();
extern Transform *CIFDirectionToTrans();
extern int CIFReadNameToType();
/* Variable argument procedures require complete prototype */
extern void CIFReadError(const char *format, ...) ATTR_FORMAT_PRINTF_1;
extern void CIFReadWarning(const char *format, ...) ATTR_FORMAT_PRINTF_1;
extern void CIFReadError(char *format, ...);
extern void CIFReadWarning(char *format, ...);
/* Variables shared by the CIF-reading modules, see CIFreadutils.c
* for more details:
@ -221,4 +197,4 @@ extern int cifParseLaChar;
? (cifParseLaAvail = FALSE, cifParseLaChar) \
: (cifParseLaChar = getc(cifInputFile)))
#endif /* _MAGIC__CIF__CIFREAD_H */
#endif /* _CIFREAD_H */

View File

@ -3,25 +3,24 @@
* This file provides procedures for displaying CIF layers on
* the screen using the highlight facilities.
*
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
*/
#ifndef lint
static const char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magic-8.0/cif/CIFsee.c,v 1.5 2010/06/24 12:37:15 tim Exp $";
static char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magic-8.0/cif/CIFsee.c,v 1.5 2010/06/24 12:37:15 tim Exp $";
#endif /* not lint */
#include <stdio.h>
#include "tcltk/tclmagic.h"
#include "utils/magic.h"
#include "utils/geometry.h"
#include "tiles/tile.h"
@ -35,9 +34,6 @@ static const char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magi
#include "textio/textio.h"
#include "utils/undo.h"
/* C99 compat */
#include "drc/drc.h"
/* The following variable holds the CellDef into which feedback
* is to be placed for displaying CIF.
*/
@ -76,9 +72,9 @@ typedef struct {
*/
int
cifPaintDBFunc(
Tile *tile, /* Tile of CIF information. */
PaintLayerData *pld)
cifPaintDBFunc(tile, pld)
Tile *tile; /* Tile of CIF information. */
PaintLayerData *pld;
{
Rect area;
int pNum;
@ -132,14 +128,14 @@ cifPaintDBFunc(
*/
void
CIFPaintLayer(
CellDef *rootDef, /* Cell for which to generate CIF. Must be
CIFPaintLayer(rootDef, area, cifLayer, magicLayer, paintDef)
CellDef *rootDef; /* Cell for which to generate CIF. Must be
* the rootDef of a window.
*/
Rect *area, /* Area in which to generate CIF. */
char *cifLayer, /* CIF layer to highlight on the screen. */
int magicLayer, /* Magic layer to paint with the result */
CellDef *paintDef) /* CellDef to paint into (may be NULL) */
Rect *area; /* Area in which to generate CIF. */
char *cifLayer; /* CIF layer to highlight on the screen. */
int magicLayer; /* Magic layer to paint with the result */
CellDef *paintDef; /* CellDef to paint into (may be NULL) */
{
int oldCount, i;
char msg[100];
@ -166,14 +162,8 @@ CIFPaintLayer(
scx.scx_trans = GeoIdentityTransform;
(void) DBTreeSrTiles(&scx, &DBAllButSpaceAndDRCBits, 0,
cifHierCopyFunc, (ClientData) CIFComponentDef);
CIFCopyMaskHints(&scx, CIFComponentDef);
DBTreeSrCells(&scx, 0, cifHierCopyMaskHints,
(ClientData)CIFComponentDef);
oldCount = DBWFeedbackCount;
CIFGen(CIFComponentDef, rootDef, area, CIFPlanes, &depend, TRUE, TRUE, FALSE,
(ClientData)NULL);
CIFGen(CIFComponentDef, area, CIFPlanes, &depend, TRUE, TRUE);
DBCellClearDef(CIFComponentDef);
/* Report any errors that occurred. */
@ -217,9 +207,9 @@ CIFPaintLayer(
*/
int
cifSeeFunc(
Tile *tile, /* Tile to be entered as feedback. */
SeeLayerData *sld) /* Layer and explanation for the feedback. */
cifSeeFunc(tile, sld)
Tile *tile; /* Tile to be entered as feedback. */
SeeLayerData *sld; /* Layer and explanation for the feedback. */
{
Rect area;
@ -258,12 +248,12 @@ cifSeeFunc(
*/
void
CIFSeeLayer(
CellDef *rootDef, /* Cell for which to generate CIF. Must be
CIFSeeLayer(rootDef, area, layer)
CellDef *rootDef; /* Cell for which to generate CIF. Must be
* the rootDef of a window.
*/
Rect *area, /* Area in which to generate CIF. */
char *layer) /* CIF layer to highlight on the screen. */
Rect *area; /* Area in which to generate CIF. */
char *layer; /* CIF layer to highlight on the screen. */
{
int oldCount, i;
char msg[100];
@ -286,13 +276,8 @@ CIFSeeLayer(
scx.scx_trans = GeoIdentityTransform;
(void) DBTreeSrTiles(&scx, &DBAllButSpaceAndDRCBits, 0,
cifHierCopyFunc, (ClientData) CIFComponentDef);
CIFCopyMaskHints(&scx, CIFComponentDef);
DBTreeSrCells(&scx, 0, cifHierCopyMaskHints,
(ClientData)CIFComponentDef);
oldCount = DBWFeedbackCount;
CIFGen(CIFComponentDef, rootDef, area, CIFPlanes, &depend, TRUE, TRUE,
FALSE, (ClientData)NULL);
CIFGen(CIFComponentDef, area, CIFPlanes, &depend, TRUE, TRUE);
DBCellClearDef(CIFComponentDef);
/* Report any errors that occurred. */
@ -326,7 +311,7 @@ CIFSeeLayer(
}
UndoEnable();
}
/*
* ----------------------------------------------------------------------------
*
@ -348,14 +333,14 @@ CIFSeeLayer(
*/
void
CIFSeeHierLayer(
CellDef *rootDef, /* Def in which to compute CIF. Must be
CIFSeeHierLayer(rootDef, area, layer, arrays, subcells)
CellDef *rootDef; /* Def in which to compute CIF. Must be
* the root definition of a window.
*/
Rect *area, /* Area in which to generate CIF. */
char *layer, /* CIF layer to be highlighted. */
bool arrays, /* TRUE means show array interactions. */
bool subcells) /* TRUE means show subcell interactions. */
Rect *area; /* Area in which to generate CIF. */
char *layer; /* CIF layer to be highlighted. */
bool arrays; /* TRUE means show array interactions. */
bool subcells; /* TRUE means show subcell interactions. */
{
int i, oldCount;
SeeLayerData sld;
@ -373,7 +358,7 @@ CIFSeeHierLayer(
CIFGenSubcells(rootDef, area, CIFPlanes);
if (arrays)
CIFGenArrays(rootDef, area, CIFPlanes);
/* Report any errors that occurred. */
if (DBWFeedbackCount != oldCount)
@ -381,7 +366,7 @@ CIFSeeHierLayer(
TxPrintf("%d problems occurred. See feedback entries.\n",
DBWFeedbackCount - oldCount);
}
(void) sprintf(msg, "CIF layer \"%s\"", layer);
cifSeeDef = rootDef;
sld.text = msg;
@ -426,11 +411,10 @@ typedef struct {
} coverstats;
void
CIFCoverageLayer(
CellDef *rootDef, /* Def in which to compute CIF coverage */
Rect *area, /* Area in which to compute coverage */
char *layer, /* CIF layer for coverage computation. */
bool dolist) /* If TRUE, report only the value, in decimal */
CIFCoverageLayer(rootDef, area, layer)
CellDef *rootDef; /* Def in which to compute CIF coverage */
Rect *area; /* Area in which to compute coverage */
char *layer; /* CIF layer for coverage computation. */
{
coverstats cstats;
int i, scale;
@ -438,7 +422,7 @@ CIFCoverageLayer(
SearchContext scx;
TileTypeBitMask mask, depend;
float fcover;
int cifCoverageFunc(Tile *tile, ClientData *arg);
int cifCoverageFunc();
bool doBox = (area != &rootDef->cd_bbox) ? TRUE : FALSE;
/* Check out the CIF layer name. */
@ -456,14 +440,9 @@ CIFCoverageLayer(
scx.scx_trans = GeoIdentityTransform;
(void) DBTreeSrTiles(&scx, &DBAllButSpaceAndDRCBits, 0,
cifHierCopyFunc, (ClientData) CIFComponentDef);
CIFCopyMaskHints(&scx, CIFComponentDef);
DBTreeSrCells(&scx, 0, cifHierCopyMaskHints,
(ClientData)CIFComponentDef);
CIFGen(CIFComponentDef, rootDef, area, CIFPlanes, &depend, TRUE, TRUE,
FALSE, (ClientData)NULL);
CIFGen(CIFComponentDef, area, CIFPlanes, &depend, TRUE, TRUE);
DBCellClearDef(CIFComponentDef);
cstats.coverage = 0;
cstats.bounds.r_xbot = cstats.bounds.r_xtop = 0;
cstats.bounds.r_ybot = cstats.bounds.r_ytop = 0;
@ -487,38 +466,24 @@ CIFCoverageLayer(
atotal = (long long)(cstats.bounds.r_xtop - cstats.bounds.r_xbot);
atotal *= (long long)(cstats.bounds.r_ytop - cstats.bounds.r_ybot);
if (dolist)
{
#ifdef MAGIC_WRAPPER
Tcl_Obj *pobj;
pobj = Tcl_NewDoubleObj((double)fcover);
Tcl_SetObjResult(magicinterp, pobj);
#else
TxPrintf("%g\n", fcover);
#endif
}
else
{
TxPrintf("%s Area = %lld CIF units^2\n", doBox ? "Cursor Box" :
TxPrintf("%s Area = %lld CIF units^2\n", doBox ? "Cursor Box" :
"Cell", btotal);
TxPrintf("Layer Bounding Area = %lld CIF units^2\n", atotal);
TxPrintf("Layer Total Area = %lld CIF units^2\n", cstats.coverage);
TxPrintf("Coverage in %s = %1.1f%%\n", doBox ? "box" :
TxPrintf("Layer Bounding Area = %lld CIF units^2\n", atotal);
TxPrintf("Layer Total Area = %lld CIF units^2\n", cstats.coverage);
TxPrintf("Coverage in %s = %1.1f%%\n", doBox ? "box" :
"cell", 100.0 * fcover);
}
}
int
cifCoverageFunc(
Tile *tile,
ClientData *arg)
cifCoverageFunc(tile, arg)
Tile *tile;
ClientData *arg;
{
coverstats *cstats = (coverstats *)arg;
Rect r;
TiToRect(tile, &r);
cstats->coverage += (long long)(r.r_xtop - r.r_xbot) * (long long)(r.r_ytop - r.r_ybot);
cstats->coverage += (long long)((r.r_xtop - r.r_xbot) * (r.r_ytop - r.r_ybot));
GeoInclude(&r, &cstats->bounds);
return(0);

File diff suppressed because it is too large Load Diff

View File

@ -3,21 +3,21 @@
*
* Output of CIF.
*
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
*/
#ifndef lint
static const char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magic-8.0/cif/CIFwrite.c,v 1.2 2010/06/24 12:37:15 tim Exp $";
static char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magic-8.0/cif/CIFwrite.c,v 1.2 2010/06/24 12:37:15 tim Exp $";
#endif /* not lint */
#include <stdlib.h>
@ -44,15 +44,14 @@ static const char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magi
#include "textio/textio.h"
/* Forward declarations */
extern int cifWriteInitFunc(CellDef *def);
extern int cifWriteMarkFunc(CellUse *use);
extern int cifWritePaintFunc(Tile *tile, FILE *f);
extern int cifWriteLabelFunc(Tile *tile, FILE *f);
extern int cifWriteUseFunc(CellUse *use, FILE *f);
extern void cifOutPreamble(FILE *outf, CellDef *cell);
extern void cifOut(FILE *outf);
extern void cifOutFunc(CellDef *def, FILE *f);
extern void GrClipTriangle(Rect *r, Rect *c, int clipped, TileType dinfo, Point *points, int *np);
extern int cifWriteInitFunc();
extern int cifWriteMarkFunc();
extern int cifWritePaintFunc();
extern int cifWriteUseFunc();
extern void cifOutPreamble();
extern void cifOut();
extern void cifOutFunc();
extern int GrClipTriangle();
/* Current cell number in CIF numbering scheme */
@ -87,7 +86,7 @@ char *CIFPathPrefix = NULL;
bool CIFHierWriteDisable = FALSE;
bool CIFArrayWriteDisable = FALSE;
/*
* ----------------------------------------------------------------------------
*
@ -118,13 +117,12 @@ bool CIFArrayWriteDisable = FALSE;
*/
bool
CIFWrite(
CellDef *rootDef, /* Pointer to CellDef to be written */
FILE *f) /* Open output file */
CIFWrite(rootDef, f)
CellDef *rootDef; /* Pointer to CellDef to be written */
FILE *f; /* Open output file */
{
bool good;
int oldCount = DBWFeedbackCount;
CellDef *err_def;
CellUse dummy;
/*
@ -134,20 +132,14 @@ CIFWrite(
*/
dummy.cu_def = rootDef;
err_def = DBCellReadArea(&dummy, &rootDef->cd_bbox, TRUE);
if (err_def != NULL)
{
TxError("Failure to read in entire subtree of the cell.\n");
TxError("Failed on cell %s.\n", err_def->cd_name);
return (FALSE);
}
DBCellReadArea(&dummy, &rootDef->cd_bbox);
DBFixMismatch();
if (CIFCurStyle->cs_reducer == 0)
{
TxError("The current CIF output style can only be used for writing\n");
TxError("Calma output. Try picking another output style.\n");
return (FALSE);
return (TRUE);
}
/*
@ -167,8 +159,8 @@ CIFWrite(
cifOutPreamble(f, rootDef);
cifOut(f);
StackFree(cifStack);
if ((int) CD2INT(rootDef->cd_client) < 0)
rootDef->cd_client = INT2CD(- (int) CD2INT(rootDef->cd_client));
if ((int) rootDef->cd_client < 0)
rootDef->cd_client = (ClientData) (- (int) rootDef->cd_client);
/* See if any problems occurred. */
@ -182,11 +174,11 @@ CIFWrite(
* Now we are almost done.
* Just output a call on the root cell
*/
fprintf(f, "C %d;\nEnd\n", (int) CD2INT(rootDef->cd_client));
fprintf(f, "C %d;\nEnd\n", (int) rootDef->cd_client);
good = !ferror(f);
return (good);
}
/*
* ----------------------------------------------------------------------------
*
@ -205,13 +197,13 @@ CIFWrite(
*/
int
cifWriteInitFunc(
CellDef *def)
cifWriteInitFunc(def)
CellDef *def;
{
def->cd_client = (ClientData) 0;
return (0);
}
/*
* ----------------------------------------------------------------------------
*
@ -229,16 +221,16 @@ cifWriteInitFunc(
*/
int
cifWriteMarkFunc(
CellUse *use)
cifWriteMarkFunc(use)
CellUse *use;
{
if (use->cu_def->cd_client != (ClientData) 0) return 0;
use->cu_def->cd_client = INT2CD(cifCellNum);
use->cu_def->cd_client = (ClientData) cifCellNum;
cifCellNum -= 1;
StackPush((ClientData) use->cu_def, cifStack);
return (0);
}
/*
* ----------------------------------------------------------------------------
*
@ -255,9 +247,9 @@ cifWriteMarkFunc(
*/
void
cifOutPreamble(
FILE *outf,
CellDef *cell)
cifOutPreamble(outf, cell)
FILE *outf;
CellDef *cell;
{
extern char *MagicVersion;
extern char *MagicCompileTime;
@ -285,7 +277,7 @@ cifOutPreamble(
fprintf(outf,"( @@style : %s );\n", CIFCurStyle->cs_name);
fprintf(outf,"( @@date : %s );\n", now);
}
/*
* ----------------------------------------------------------------------------
*
@ -304,24 +296,24 @@ cifOutPreamble(
*/
void
cifOut(
FILE *outf)
cifOut(outf)
FILE *outf;
{
CellDef *def;
bool needHier;
while (!StackEmpty(cifStack))
{
def = (CellDef *) StackPop(cifStack);
if ((int) CD2INT(def->cd_client) >= 0) continue; /* Already output */
if ((int) def->cd_client >= 0) continue; /* Already output */
if (SigInterruptPending) continue;
def->cd_client = INT2CD(- (int) CD2INT(def->cd_client));
def->cd_client = (ClientData) (- (int) def->cd_client);
/* Read the cell in if it is not already available. */
if ((def->cd_flags & CDAVAILABLE) == 0)
if (!DBCellRead(def, TRUE, TRUE, NULL))
continue;
{
if (!DBCellRead(def, (char *) NULL, TRUE, NULL)) continue;
}
/* Add any subcells to the stack. This must be done before
* outputting CIF to make sure that the subcells all have
@ -335,7 +327,7 @@ cifOut(
cifOutFunc(def, outf);
}
}
/*
* ----------------------------------------------------------------------------
*
@ -353,16 +345,16 @@ cifOut(
*/
void
cifOutFunc(
CellDef *def, /* Pointer to cell def to be written */
FILE *f) /* Open output file */
cifOutFunc(def, f)
CellDef *def; /* Pointer to cell def to be written */
FILE *f; /* Open output file */
{
Rect bigArea;
Label *lab;
int type;
CIFLayer *layer;
fprintf(f, "DS %d %d %d;\n", (int) CD2INT(def->cd_client),
fprintf(f, "DS %d %d %d;\n", (int) def->cd_client,
CIFCurStyle->cs_reducer, 2 * CIFCurStyle->cs_expander);
if (def->cd_name != (char *) NULL)
@ -382,31 +374,23 @@ cifOutFunc(
* Output all the tiles associated with this cell. Skip temporary
* layers.
*/
GEO_EXPAND(&def->cd_bbox, CIFCurStyle->cs_radius, &bigArea);
CIFErrorDef = def;
CIFGen(def, def, &bigArea, CIFPlanes, &DBAllTypeBits, TRUE, TRUE, FALSE,
(ClientData)NULL);
CIFGen(def, &bigArea, CIFPlanes, &DBAllTypeBits, TRUE, TRUE);
if (!CIFHierWriteDisable)
CIFGenSubcells(def, &bigArea, CIFPlanes);
CIFGenSubcells(def, &bigArea, CIFPlanes);
if (!CIFArrayWriteDisable)
CIFGenArrays(def, &bigArea, CIFPlanes);
CIFGenArrays(def, &bigArea, CIFPlanes);
for (type = 0; type < CIFCurStyle->cs_nLayers; type++)
{
layer = CIFCurStyle->cs_layers[type];
if (layer->cl_flags & CIF_TEMP) continue;
cifPaintLayerName = layer->cl_name;
cifPaintScale = 1;
if (layer->cl_flags & CIF_LABEL)
DBSrPaintArea((Tile *) NULL, CIFPlanes[type],
&TiPlaneRect, &CIFSolidBits, cifWriteLabelFunc,
(ClientData) f);
else
DBSrPaintArea((Tile *) NULL, CIFPlanes[type],
&TiPlaneRect, &CIFSolidBits, cifWritePaintFunc,
(ClientData) f);
(void) DBSrPaintArea((Tile *) NULL, CIFPlanes[type],
&TiPlaneRect, &CIFSolidBits, cifWritePaintFunc,
(ClientData) f);
}
/* Output labels */
@ -465,7 +449,7 @@ cifOutFunc(
(void) DBCellEnum(def, cifWriteUseFunc, (ClientData) f);
fprintf(f, "DF;\n");
}
/*
* ----------------------------------------------------------------------------
*
@ -484,16 +468,16 @@ cifOutFunc(
*/
int
cifWriteUseFunc(
CellUse *use,
FILE *f)
cifWriteUseFunc(use, f)
CellUse *use;
FILE *f;
{
int x, y, topx, topy;
int realx, realy;
Transform *t;
int cifnum;
cifnum = (int) CD2INT(use->cu_def->cd_client);
cifnum = (int) use->cu_def->cd_client;
if (cifnum < 0) cifnum = (-cifnum);
topx = use->cu_xhi - use->cu_xlo;
if (topx < 0) topx = -topx;
@ -510,7 +494,7 @@ cifWriteUseFunc(
* use identifier, which should include array subscripting
* information.
*/
/*
* Insert a 91 user command to label the next cell
*/
@ -562,68 +546,7 @@ cifWriteUseFunc(
}
return 0;
}
/*
* ----------------------------------------------------------------------------
*
* cifWriteLabelFunc --
*
* Filter function used to write out a label corresponding to a
* single paint tile. The CIF layer name is used as the label to
* output.
*
* Results:
* Always return 0
*
* Side effects:
* Writes to the disk file.
*
* ----------------------------------------------------------------------------
*/
int
cifWriteLabelFunc(
Tile *tile, /* Tile to be written out. */
FILE *f) /* File in which to write. */
{
Rect r;
int type;
Point center, size;
if (IsSplit(tile)) return 0; /* Ignore non-manhattan tiles */
if (cifPaintLayerName == NULL) return 0; /* Shouldn't happen */
TiToRect(tile, &r);
type = CIFCurStyle->cs_labelLayer[TiGetType(tile)];
center.p_x = r.r_xbot + r.r_xtop;
center.p_y = r.r_ybot + r.r_ytop;
center.p_x *= CIFCurStyle->cs_scaleFactor;
center.p_x /= CIFCurStyle->cs_reducer;
center.p_y *= CIFCurStyle->cs_scaleFactor;
center.p_y /= CIFCurStyle->cs_reducer;
if (CIFDoAreaLabels)
{
size.p_x = r.r_xtop - r.r_xbot;
size.p_y = r.r_ytop - r.r_ybot;
size.p_x *= 2 * CIFCurStyle->cs_scaleFactor;
size.p_x /= CIFCurStyle->cs_reducer;
size.p_y *= 2 * CIFCurStyle->cs_scaleFactor;
size.p_y /= CIFCurStyle->cs_reducer;
fprintf(f, "95 %s %d %d %d %d;\n",
cifPaintLayerName, size.p_x, size.p_y, center.p_x, center.p_y);
}
else
{
fprintf(f, "94 %s %d %d;\n",
cifPaintLayerName, center.p_x, center.p_y);
}
return 0;
}
/*
* ----------------------------------------------------------------------------
*
@ -641,9 +564,9 @@ cifWriteLabelFunc(
*/
int
cifWritePaintFunc(
Tile *tile, /* Tile to be written out. */
FILE *f) /* File in which to write. */
cifWritePaintFunc(tile, f)
Tile *tile; /* Tile to be written out. */
FILE *f; /* File in which to write. */
{
Rect r;
@ -691,15 +614,15 @@ cifWritePaintFunc(
CIFRects += 1;
return 0;
}
/*
* ----------------------------------------------------------------------------
*
* CIFWriteFlat --
*
* Write out the entire tree rooted at the supplied CellDef in CIF format,
* to the specified file, but write non-hierarchical CIF.
*
* to the specified file, but write non-hierarchical CIF.
*
* Results:
* TRUE if the cell could be written successfully, FALSE otherwise.
*
@ -711,9 +634,9 @@ cifWritePaintFunc(
*
* Algorithm:
* We operate on the cell in chunks chosen to keep the memory utilization
* reasonable. Foreach chunk, we use DBTreeSrTiles and cifHierCopyFunc to
* flatten the
* chunk into a yank buffer ("eliminating" the subcell problem), then use
* reasonable. Foreach chunk, we use DBTreeSrTiles and cifHierCopyFunc to
* flatten the
* chunk into a yank buffer ("eliminating" the subcell problem), then use
* cifOut to generate the CIF.
* No hierarchical design rule checking or bounding box computation
* occur during this operation -- both are explicitly avoided.
@ -722,9 +645,9 @@ cifWritePaintFunc(
*/
bool
CIFWriteFlat(
CellDef *rootDef, /* Pointer to CellDef to be written */
FILE *f) /* Open output file */
CIFWriteFlat(rootDef, f)
CellDef *rootDef; /* Pointer to CellDef to be written */
FILE *f; /* Open output file */
{
bool good;
int oldCount = DBWFeedbackCount;
@ -741,11 +664,11 @@ CIFWriteFlat(
cifOutPreamble(f, rootDef);
/*
* Now process each chunk. We cheat and use cifOut(), so we need to have
* Now process each chunk. We cheat and use cifOut(), so we need to have
* a stack for the single flattened "component" to be on.
*/
{
{
scx.scx_use = CIFDummyUse;
scx.scx_trans = GeoIdentityTransform;
GEO_EXPAND(&rootDef->cd_bbox, CIFCurStyle->cs_radius, &scx.scx_area);
@ -773,10 +696,10 @@ CIFWriteFlat(
* Just output a call on the root cell
*/
fprintf(f, "C %d;\nEnd\n", (int) CD2INT(CIFComponentDef->cd_client));
fprintf(f, "C %d;\nEnd\n", (int) CIFComponentDef->cd_client);
DBCellClearDef(CIFComponentDef);
good = !ferror(f);
/* Report any errors that occurred. */
if (DBWFeedbackCount != oldCount)

45
cif/Depend Normal file
View File

@ -0,0 +1,45 @@
CIFgen.o: CIFgen.c ../utils/magic.h ../utils/geometry.h ../tiles/tile.h \
../utils/hash.h ../database/database.h ../cif/CIFint.h ../calma/calma.h \
../commands/commands.h ../windows/windows.h ../select/selInt.h \
../utils/stack.h ../utils/malloc.h ../utils/maxrect.h
CIFhier.o: CIFhier.c ../utils/magic.h ../utils/geometry.h ../tiles/tile.h \
../utils/hash.h ../database/database.h ../cif/CIFint.h ../cif/cif.h \
../drc/drc.h ../textio/textio.h ../utils/undo.h ../utils/malloc.h \
../utils/signals.h
CIFmain.o: CIFmain.c ../tcltk/tclmagic.h ../utils/magic.h \
../utils/geometry.h ../tiles/tile.h ../utils/hash.h \
../database/database.h ../cif/CIFint.h ../textio/textio.h \
../windows/windows.h ../dbwind/dbwind.h ../utils/styles.h
CIFrdcl.o: CIFrdcl.c ../utils/magic.h ../utils/malloc.h \
../utils/geometry.h ../tiles/tile.h ../utils/hash.h ../utils/undo.h \
../database/database.h ../cif/CIFint.h ../cif/CIFread.h ../utils/utils.h \
../windows/windows.h ../dbwind/dbwind.h ../utils/main.h ../drc/drc.h
CIFrdpt.o: CIFrdpt.c ../utils/magic.h ../utils/geometry.h ../tiles/tile.h \
../utils/hash.h ../utils/malloc.h ../database/database.h \
../windows/windows.h ../utils/main.h ../cif/CIFint.h ../cif/CIFread.h
CIFrdpoly.o: CIFrdpoly.c ../utils/magic.h ../utils/geometry.h \
../tiles/tile.h ../utils/hash.h ../database/database.h ../cif/CIFint.h \
../cif/CIFread.h ../utils/malloc.h
CIFrdtech.o: CIFrdtech.c ../tcltk/tclmagic.h ../utils/magic.h \
../utils/geometry.h ../tiles/tile.h ../utils/hash.h \
../database/database.h ../utils/tech.h ../textio/textio.h \
../utils/utils.h ../cif/CIFint.h ../cif/CIFread.h ../calma/calmaInt.h \
../utils/malloc.h
CIFrdutils.o: CIFrdutils.c ../utils/magic.h ../utils/geometry.h \
../tiles/tile.h ../utils/hash.h ../database/database.h ../cif/CIFint.h \
../cif/CIFread.h ../cif/cif.h ../textio/textio.h ../utils/signals.h \
../utils/undo.h ../utils/malloc.h
CIFsee.o: CIFsee.c ../utils/magic.h ../utils/geometry.h ../tiles/tile.h \
../utils/hash.h ../database/database.h ../windows/windows.h \
../graphics/graphics.h ../dbwind/dbwind.h ../utils/styles.h \
../cif/CIFint.h ../textio/textio.h ../utils/undo.h
CIFtech.o: CIFtech.c ../utils/magic.h ../utils/geometry.h ../tiles/tile.h \
../utils/hash.h ../database/database.h ../utils/tech.h ../utils/utils.h \
../utils/styles.h ../cif/CIFint.h ../calma/calmaInt.h ../textio/textio.h \
../utils/malloc.h ../cif/cif.h ../drc/drc.h
CIFwrite.o: CIFwrite.c ../utils/magic.h ../utils/geometry.h \
../tiles/tile.h ../utils/utils.h ../utils/hash.h ../database/database.h \
../database/databaseInt.h ../utils/tech.h ../utils/stack.h \
../utils/undo.h ../cif/cif.h ../cif/CIFint.h ../utils/signals.h \
../windows/windows.h ../dbwind/dbwind.h ../utils/styles.h \
../textio/textio.h

View File

@ -4,24 +4,24 @@
* This procedure defines things that are exported by the
* cif module to the rest of the world.
*
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
*
*
* rcsid "$Header: /usr/cvsroot/magic-8.0/cif/cif.h,v 1.4 2010/06/24 12:37:15 tim Exp $
*/
#ifndef _MAGIC__CIF__CIF_H
#define _MAGIC__CIF__CIF_H
#ifndef _CIF_H
#define _CIF_H
#include "database/database.h"
@ -30,10 +30,6 @@
* depends on the size of the layout.
*/
/* Passed to CIFPaintCurrent() for print statement formatting */
#define FILE_CIF 0
#define FILE_CALMA 1
/* Exported global variables (commands/CmdCD.c) */
extern int CIFWarningLevel;
@ -51,48 +47,42 @@ extern bool CIFUnfracture;
/* Procedures that parse the cif sections of a technology file. */
extern void CIFTechStyleInit(void);
extern void CIFTechInit(void);
extern bool CIFTechLine(char *sectionName, int argc, char *argv[]);
extern void CIFTechFinal(void);
extern void CIFTechOutputScale(int n, int d);
extern int CIFTechInputScale(int n, int d, bool opt);
extern bool CIFTechLimitScale(int ns, int ds);
extern void CIFReadTechStyleInit(void);
extern void CIFReadTechInit(void);
extern bool CIFReadTechLine(char *sectionName, int argc, char *argv[]);
extern void CIFReadTechFinal(void);
extern void CIFParseReadLayers(char *string, TileTypeBitMask *mask, bool newok);
extern void CIFTechStyleInit();
extern void CIFTechInit();
extern bool CIFTechLine();
extern void CIFTechFinal();
extern void CIFTechOutputScale();
extern void CIFTechInputScale();
extern bool CIFTechLimitScale();
extern void CIFReadTechStyleInit();
extern void CIFReadTechInit();
extern bool CIFReadTechLine();
extern void CIFReadTechFinal();
/* Externally-visible procedures: */
extern float CIFGetOutputScale(int convert);
extern float CIFGetScale(int convert);
extern float CIFGetInputScale(int convert);
extern float CIFGetOutputScale();
extern float CIFGetInputScale();
extern int CIFGetDefaultContactSize();
extern int CIFPaintCurrent(int filetype);
extern void CIFSeeLayer(CellDef *rootDef, Rect *area, char *layer);
extern void CIFPaintLayer(CellDef *rootDef, Rect *area, char *cifLayer, int magicLayer, CellDef *paintDef);
extern void CIFSeeHierLayer(CellDef *rootDef, Rect *area, char *layer, int arrays, int subcells);
extern void CIFPrintStats(void);
extern int CIFPaintCurrent();
extern void CIFSeeLayer();
extern void CIFPaintLayer();
extern void CIFSeeHierLayer();
extern void CIFPrintStats();
extern bool CIFWrite(CellDef *rootDef, FILE *f);
extern void CIFReadFile(FILE *file);
extern bool CIFWrite();
extern void CIFReadFile();
extern void CIFSetStyle(char *name);
extern void CIFSetReadStyle(char *name);
extern void CIFSetStyle();
extern void CIFSetReadStyle();
extern void CIFPrintStyle(bool dolist, bool doforall, bool docurrent);
extern void CIFPrintReadStyle(bool dolist, bool doforall, bool docurrent);
extern void CIFPrintStyle();
extern void CIFPrintReadStyle();
extern int CIFOutputScaleFactor(void);
extern int CIFOutputScaleFactor();
extern void PaintWireList(Point *pointlist, int number, int width, int endcap, Plane *plane,
PaintResultType *ptable, PaintUndoInfo *ui);
extern LinkedRect *PaintPolygon(Point *pointlist, int number, Plane *plane, PaintResultType *ptable,
PaintUndoInfo *ui, int keep);
extern void PaintWireList();
extern LinkedRect *PaintPolygon();
/* C99 compat */
extern int CIFGetContactSize(TileType type, int *edge, int *spacing, int *border);
#endif /* _MAGIC__CIF__CIF_H */
#endif /* _CIF_H */

View File

@ -3,21 +3,21 @@
*
* Commands for the color map editor.
*
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
*/
#ifndef lint
static const char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magic-8.0/cmwind/CMWcmmnds.c,v 1.1.1.1 2008/02/03 20:43:50 tim Exp $";
static char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magic-8.0/cmwind/CMWcmmnds.c,v 1.1.1.1 2008/02/03 20:43:50 tim Exp $";
#endif /* not lint */
#include <stdio.h>
@ -43,11 +43,10 @@ static const char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magi
/* Forward declarations: */
extern void cmwButtonUp(MagWindow *w, Point *p, int button);
extern void cmwButtonDown(MagWindow *w, Point *p, int button);
extern void cbUpdate(MagWindow *w, int code, double x, int replace);
extern bool RGBxHSV(double r, double g, double b, double *h, double *s, double *v);
extern void HSVxRGB(double h, double s, double v, double *r, double *g, double *b);
extern void cmwButtonUp(), cmwButtonDown();
extern void cbUpdate();
extern void RGBxHSV();
extern void HSVxRGB();
/* If a button is pressed over the top box in the window, which
* displays the current color, we must save the window in which
@ -65,7 +64,7 @@ bool cmwWatchButtonUp;
bool cmwModified = FALSE;
/*
* ----------------------------------------------------------------------------
*
@ -85,9 +84,9 @@ bool cmwModified = FALSE;
*/
void
CMWcommand(
MagWindow *w,
TxCommand *cmd)
CMWcommand(w, cmd)
MagWindow *w;
TxCommand *cmd;
{
switch (cmd->tx_button)
{
@ -138,13 +137,13 @@ CMWcommand(
*/
void
cmwButtonDown(
MagWindow *w, /* Window where the button was pressed. */
Point *p,
int button)
cmwButtonDown(w, p, button)
MagWindow *w; /* Window where the button was pressed. */
Point *p;
int button;
{
const ColorBar *cb;
const ColorPump *cp;
ColorBar *cb;
ColorPump *cp;
Point surfacePoint;
int x;
double dx;
@ -195,7 +194,7 @@ cmwButtonDown(
/* See if the cursor is over the current color area. If so, remember
* the fact and wait for the button to be released.
*/
if (GEO_ENCLOSE(&surfacePoint, &cmwCurrentColorArea))
{
cmwWindow = w;
@ -225,20 +224,20 @@ cmwButtonDown(
*/
void
cmwButtonUp(
MagWindow *w, /* Window where the button was released */
Point *p, /* Point where button was released, in window coords.*/
int button) /* Button that was released. */
cmwButtonUp(w, p, button)
MagWindow *w; /* Window where the button was released */
Point *p; /* Point where button was released, in window coords.*/
int button; /* Button that was released. */
{
CMWclientRec *crec;
int r, g, b, color, oldR, oldG, oldB;
extern int cmwRedisplayFunc(MagWindow *w, int color);
extern int cmwRedisplayFunc();
/* If the button wasn't depressed over the top box in the window
* (the one displaying the current color), then we ignore the
* button release.
*/
if (!cmwWatchButtonUp) return;
cmwWatchButtonUp = FALSE;
@ -247,7 +246,7 @@ cmwButtonUp(
* color values from the pixel underneath the cursor to the current
* color.
*/
/* Read the pixel from the window that was underneath the cursor when
* the button was released.
*/
@ -297,12 +296,12 @@ cmwButtonUp(
*/
void
cmwPushbutton(
MagWindow *w,
TxCommand *cmd)
cmwPushbutton(w, cmd)
MagWindow *w;
TxCommand *cmd;
{
int button;
static const char * const cmwButton[] = {"left", "middle", "right", NULL};
static char *cmwButton[] = {"left", "middle", "right", NULL};
if (cmd->tx_argc != 2)
{
@ -356,9 +355,9 @@ cmwPushbutton(
*/
void
cmwColor(
MagWindow *w,
TxCommand *cmd)
cmwColor(w, cmd)
MagWindow *w;
TxCommand *cmd;
{
int color, r, g, b;
CMWclientRec *crec;
@ -373,7 +372,7 @@ cmwColor(
}
else if (cmd->tx_argc == 2)
{
if (sscanf(cmd->tx_argv[1], "%i", &color) != 1)
if (sscanf(cmd->tx_argv[1], "%i", &color) == 0)
{
/* Invalid color---allow keywords "next" and "last" */
crec = (CMWclientRec *) w->w_clientData;
@ -427,10 +426,10 @@ cmwColor(
}
CMWloadWindow(w, color);
}
else
else
TxError("Usage: color [#|next|last|get|rgb]\n");
}
/*
* ----------------------------------------------------------------------------
*
@ -451,9 +450,9 @@ cmwColor(
*/
void
cmwSave(
MagWindow *w,
TxCommand *cmd)
cmwSave(w, cmd)
MagWindow *w;
TxCommand *cmd;
{
bool ok;
if ((cmd->tx_argc != 1) && (cmd->tx_argc != 4))
@ -474,7 +473,7 @@ cmwSave(
}
if (ok) cmwModified = FALSE;
}
/*
* ----------------------------------------------------------------------------
*
@ -496,9 +495,9 @@ cmwSave(
*/
void
cmwLoad(
MagWindow *w,
TxCommand *cmd)
cmwLoad(w, cmd)
MagWindow *w;
TxCommand *cmd;
{
if ((cmd->tx_argc != 1) && (cmd->tx_argc != 4))
{
@ -515,7 +514,7 @@ cmwLoad(
else (void) GrReadCMap(DBWStyleType, (char *) NULL,
MainMonType, ".", SysLibPath);
}
/*
* ----------------------------------------------------------------------------
*
@ -538,18 +537,18 @@ cmwLoad(
*/
void
cbUpdate(
MagWindow *w, /* Window whose color is to be changed. */
int code, /* Indicates which color component to change. */
double x, /* Gives increment or new value for color. */
int replace) /* TRUE means replace component with x, FALSE
cbUpdate(w, code, x, replace)
MagWindow *w; /* Window whose color is to be changed. */
int code; /* Indicates which color component to change. */
double x; /* Gives increment or new value for color. */
int replace; /* TRUE means replace component with x, FALSE
* means increment component by x.
*/
{
CMWclientRec *cr = (CMWclientRec *) w->w_clientData;
double values[6];
int r, g, b, nr, ng, nb;
extern int cmwRedisplayFunc(MagWindow *w, int color);
extern int cmwRedisplayFunc();
/* Get current color map values */
(void) GrGetColor(cr->cmw_color, &r, &g, &b);
@ -592,14 +591,14 @@ cbUpdate(
}
int
cmwRedisplayFunc(
MagWindow *w, /* Window that may have to be redisplayed. */
int color) /* If this color is in window, redisplay the
cmwRedisplayFunc(w, color)
MagWindow *w; /* Window that may have to be redisplayed. */
int color; /* If this color is in window, redisplay the
* color bars in the window.
*/
{
const ColorBar *cb;
const ColorPump *cp;
ColorBar *cb;
ColorPump *cp;
Rect screenR;
CMWclientRec *cr = (CMWclientRec *) w->w_clientData;
@ -645,11 +644,11 @@ cmwRedisplayFunc(
*/
bool
CMWCheckWritten(void)
CMWCheckWritten()
{
bool indx;
char *prompt;
static const char * const yesno[] = {"no", "yes", NULL};
static char *(yesno[]) = {"no", "yes", NULL};
if (!cmwModified) return TRUE;
prompt = TxPrintString("The color map has been modified.\n"

View File

@ -4,21 +4,21 @@
* Procedures to interface the colormap editor with the window package
* for the purposes of window creation, deletion, and modification.
*
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
*/
#ifndef lint
static const char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magic-8.0/cmwind/CMWmain.c,v 1.1.1.1 2008/02/03 20:43:50 tim Exp $";
static char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magic-8.0/cmwind/CMWmain.c,v 1.1.1.1 2008/02/03 20:43:50 tim Exp $";
#endif /* not lint */
#include <stdio.h>
@ -44,12 +44,12 @@ global WindClient CMWclientID;
/* Forward and external declarations */
extern void cmwColor(MagWindow *w, TxCommand *cmd);
extern void cmwSave(MagWindow *w, TxCommand *cmd);
extern void cmwLoad(MagWindow *w, TxCommand *cmd);
extern void cmwPushbutton(MagWindow *w, TxCommand *cmd);
extern bool RGBxHSV(double r, double g, double b, double *h, double *s, double *v);
extern void CMWundoInit(void);
extern void cmwColor();
extern void cmwSave();
extern void cmwLoad();
extern void cmwPushbutton();
extern void RGBxHSV();
extern void CMWundoInit();
/* -------------------------------------------------------------------- */
@ -71,7 +71,7 @@ extern void CMWundoInit(void);
* | | - | | | | + | | - | | | | + | |
* | +---+ +----------------+ +---+ +---+ +----------------+ +---+ |
* | |
* | Blue Value
* | Blue Value
* | +---+ +----------------+ +---+ +---+ +----------------+ +---+ |
* | | - | | | | + | | - | | | | + | |
* | +---+ +----------------+ +---+ +---+ +----------------+ +---+ |
@ -89,54 +89,54 @@ extern void CMWundoInit(void);
* which pump is hit and which mouse button is used to hit it.
*/
const ColorBar colorBars[] =
ColorBar colorBars[] =
{
{"Red", CB_RED, STYLE_RED, {{ 2000, 8000}, {10000, 9000}},
{{ 2000, 9500}, {10000, 10500}}},
{"Green", CB_GREEN, STYLE_GREEN, {{ 2000, 5000}, {10000, 6000}},
{{ 2000, 6500}, {10000, 7500}}},
{"Blue", CB_BLUE, STYLE_BLUE, {{ 2000, 2000}, {10000, 3000}},
{{ 2000, 3500}, {10000, 4500}}},
{"Hue", CB_HUE, STYLE_YELLOW, {{14000, 8000}, {22000, 9000}},
{{14000, 9500}, {22000, 10500}}},
{"Saturation", CB_SAT, STYLE_GRAY, {{14000, 5000}, {22000, 6000}},
{{14000, 6500}, {22000, 7500}}},
{"Value", CB_VALUE, STYLE_BROWN1, {{14000, 2000}, {22000, 3000}},
{{14000, 3500}, {22000, 4500}}},
{0}
"Red", CB_RED, STYLE_RED, {2000, 8000, 10000, 9000},
{2000, 9500, 10000, 10500},
"Green", CB_GREEN, STYLE_GREEN, {2000, 5000, 10000, 6000},
{2000, 6500, 10000, 7500},
"Blue", CB_BLUE, STYLE_BLUE, {2000, 2000, 10000, 3000},
{2000, 3500, 10000, 4500},
"Hue", CB_HUE, STYLE_YELLOW, {14000, 8000, 22000, 9000},
{14000, 9500, 22000, 10500},
"Saturation", CB_SAT, STYLE_GRAY, {14000, 5000, 22000, 6000},
{14000, 6500, 22000, 7500},
"Value", CB_VALUE, STYLE_BROWN1, {14000, 2000, 22000, 3000},
{14000, 3500, 22000, 4500},
0
};
const ColorPump colorPumps[] =
ColorPump colorPumps[] =
{
{CB_RED, -.0078, {{ 500, 8000}, { 1500, 9000}}},
{CB_RED, .0078, {{10500, 8000}, {11500, 9000}}},
{CB_GREEN, -.0078, {{ 500, 5000}, { 1500, 6000}}},
{CB_GREEN, .0078, {{10500, 5000}, {11500, 6000}}},
{CB_BLUE, -.0078, {{ 500, 2000}, { 1500, 3000}}},
{CB_BLUE, .0078, {{10500, 2000}, {11500, 3000}}},
{CB_HUE, -.01, {{12500, 8000}, {13500, 9000}}},
{CB_HUE, .01, {{22500, 8000}, {23500, 9000}}},
{CB_SAT, -.01, {{12500, 5000}, {13500, 6000}}},
{CB_SAT, .01, {{22500, 5000}, {23500, 6000}}},
{CB_VALUE, -.01, {{12500, 2000}, {13500, 3000}}},
{CB_VALUE, .01, {{22500, 2000}, {23500, 3000}}},
{-1}
CB_RED, -.0078, {500, 8000, 1500, 9000},
CB_RED, .0078, {10500, 8000, 11500, 9000},
CB_GREEN, -.0078, {500, 5000, 1500, 6000},
CB_GREEN, .0078, {10500, 5000, 11500, 6000},
CB_BLUE, -.0078, {500, 2000, 1500, 3000},
CB_BLUE, .0078, {10500, 2000, 11500, 3000},
CB_HUE, -.01, {12500, 8000, 13500, 9000},
CB_HUE, .01, {22500, 8000, 23500, 9000},
CB_SAT, -.01, {12500, 5000, 13500, 6000},
CB_SAT, .01, {22500, 5000, 23500, 6000},
CB_VALUE, -.01, {12500, 2000, 13500, 3000},
CB_VALUE, .01, {22500, 2000, 23500, 3000},
-1
};
const Rect cmwCurrentColorArea = {{6000, 12000}, {18000, 15000}};
const Rect cmwCurrentColorTextBox = {{6000, 15500}, {18000, 16500}};
const char * const cmwCurrentColorText = "Color Being Edited";
Rect cmwCurrentColorArea = {{6000, 12000}, {18000, 15000}};
Rect cmwCurrentColorTextBox = {{6000, 15500}, {18000, 16500}};
char *cmwCurrentColorText = "Color Being Edited";
/* Bounding rectangle for entire window */
const Rect colorWindowRect = {{0, 1500}, {24000, 17000}};
Rect colorWindowRect = {{0, 1500}, {24000, 17000}};
/*
* ----------------------------------------------------------------------------
*
* CMWcreate --
*
* A new window has been created. Create and initialize the needed
* A new window has been created. Create and initialize the needed
* structures.
*
* Results:
@ -149,13 +149,13 @@ const Rect colorWindowRect = {{0, 1500}, {24000, 17000}};
*/
bool
CMWcreate(
MagWindow *window,
int argc,
char *argv[])
CMWcreate(window, argc, argv)
MagWindow *window;
int argc;
char *argv[];
{
CMWclientRec *crec;
unsigned int color;
int color;
crec = (CMWclientRec *) mallocMagic(sizeof(CMWclientRec));
window->w_clientData = (ClientData) crec;
@ -171,7 +171,7 @@ CMWcreate(
CMWloadWindow(window, color);
return (TRUE);
}
/*
* ----------------------------------------------------------------------------
*
@ -189,8 +189,8 @@ CMWcreate(
*/
bool
CMWdelete(
MagWindow *window)
CMWdelete(window)
MagWindow *window;
{
CMWclientRec *cr;
@ -200,7 +200,7 @@ CMWdelete(
freeMagic((char *) cr);
return (TRUE);
}
/*
* ----------------------------------------------------------------------------
*
@ -218,16 +218,16 @@ CMWdelete(
*/
void
CMWreposition(
MagWindow *window,
Rect *newScreenArea,
bool final)
CMWreposition(window, newScreenArea, final)
MagWindow *window;
Rect *newScreenArea;
bool final;
{
if (final)
WindMove(window, &colorWindowRect);
}
/*
* ----------------------------------------------------------------------------
*
@ -244,14 +244,14 @@ CMWreposition(
*/
void
CMWredisplay(
MagWindow *w, /* The window containing the area. */
Rect *rootArea, /* Redisplay area in surface coordinates. */
Rect *clipArea) /* An area on the screen to clip to. */
CMWredisplay(w, rootArea, clipArea)
MagWindow *w; /* The window containing the area. */
Rect *rootArea; /* Redisplay area in surface coordinates. */
Rect *clipArea; /* An area on the screen to clip to. */
{
CMWclientRec *cr;
const ColorBar *cb;
const ColorPump *cp;
ColorBar *cb;
ColorPump *cp;
Rect rect, screenR;
Point screenP;
double values[6], x;
@ -332,7 +332,7 @@ CMWredisplay(
* to that color. Instead, change the color in a particular style
* reserved for our own use.
*/
if (GEO_TOUCH(&cmwCurrentColorArea, rootArea))
{
GrStyleTable[STYLE_CMEDIT].color = cr->cmw_color;
@ -353,7 +353,7 @@ CMWredisplay(
GrUnlock(w);
}
/*
* ----------------------------------------------------------------------------
*
@ -372,9 +372,9 @@ CMWredisplay(
*/
void
CMWloadWindow(
MagWindow *w, /* Identifies window to which color is to be bound */
int color) /* New color to be bound to this window. */
CMWloadWindow(w, color)
MagWindow *w; /* Identifies window to which color is to be bound */
int color; /* New color to be bound to this window. */
{
CMWclientRec *cr = (CMWclientRec *) w->w_clientData;
char caption[40];
@ -389,7 +389,7 @@ CMWloadWindow(
/* move the contents of the window so the color bars show */
WindMove(w, &colorWindowRect);
}
/*
* ----------------------------------------------------------------------------
*
@ -407,7 +407,7 @@ CMWloadWindow(
*/
void
CMWinit(void)
CMWinit()
{
CMWclientID = WindAddClient("color", CMWcreate, CMWdelete,
CMWredisplay, CMWcommand,

View File

@ -4,21 +4,21 @@
* Procedures to translate between RGB color space and HSV color space.
* Courtesy of Ken Fishkin.
*
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
*/
#ifndef lint
static const char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magic-8.0/cmwind/CMWrgbhsv.c,v 1.1.1.1 2008/02/03 20:43:50 tim Exp $";
static char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magic-8.0/cmwind/CMWrgbhsv.c,v 1.1.1.1 2008/02/03 20:43:50 tim Exp $";
#endif /* not lint */
#include <stdio.h>
@ -45,13 +45,9 @@ static const char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magi
*/
bool
RGBxHSV(
double r,
double g,
double b,
double *h,
double *s,
double *v)
RGBxHSV( r, g, b, h, s, v)
double r, g, b;
double *h, *s, *v;
{
double max, delta;
double mr,mg,mb;
@ -94,14 +90,10 @@ RGBxHSV(
#define SETRGB(rr,gg,bb) *r=rr;*g=gg;*b=bb
void
HSVxRGB(
double h,
double s,
double v,
double *r,
double *g,
double *b)
{
HSVxRGB( h,s,v,r,g,b)
double h,s,v;
double *r,*g,*b;
{
double f,m,n,k;
int i;
double vs,vsf;
@ -133,13 +125,9 @@ HSVxRGB(
*/
bool
RGBxHSL(
double r,
double g,
double b,
double *h,
double *s,
double *l)
RGBxHSL( r, g, b, h, s, l )
double r, g, b;
double *h, *s, *l;
{
double min, max;
double delta, mr, mg, mb;
@ -196,13 +184,9 @@ RGBxHSL(
*/
void
HSLxRGB(
double h,
double s,
double l,
double *r,
double *g,
double *b)
HSLxRGB( h, s, l, r, g, b )
double h, s, l;
double *r, *g, *b;
{
double min;
double v;
@ -210,7 +194,7 @@ HSLxRGB(
int i;
double vsf;
if ( l <= 0.5)
if ( l <= 0.5)
v = l * (1.0 + s);
else
v = l + s - l*s;
@ -251,11 +235,9 @@ HSLxRGB(
*/
void
Correct_chromaticity(
double *x,
double *y,
double wx,
double wy)
Correct_chromaticity(x, y, wx, wy)
double *x,*y;
double wx,wy;
{
double oldx,oldy;
double slope;
@ -279,13 +261,9 @@ Correct_chromaticity(
*/
void
xyz_to_mrgb(
double x,
double y,
double z,
double *mr,
double *mg,
double *mb)
xyz_to_mrgb(x, y, z, mr, mg, mb)
double x, y, z;
double *mr, *mg, *mb;
{
*mr = 2.4513*x - 1.2249*y - 0.3237*z;
*mg = -1.4746*x + 2.5052*y + 0.0596*z;
@ -303,10 +281,8 @@ xyz_to_mrgb(
*/
void
Make_mRGB_Nice(
double *mR,
double *mG,
double *mB)
Make_mRGB_Nice(mR,mG,mB)
double *mR,*mG,*mB;
{
double min,max;
double mr, mg, mb;

View File

@ -3,21 +3,21 @@
*
* Interface to the undo package for the color map editor.
*
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
*/
#ifndef lint
static const char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magic-8.0/cmwind/CMWundo.c,v 1.1.1.1 2008/02/03 20:43:50 tim Exp $";
static char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magic-8.0/cmwind/CMWundo.c,v 1.1.1.1 2008/02/03 20:43:50 tim Exp $";
#endif /* not lint */
#include <stdio.h>
@ -35,6 +35,12 @@ static const char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magi
*/
UndoType cmwUndoClientID;
/*
* Functions to play events forward/backward.
*/
void cmwUndoForw(), cmwUndoBack();
void cmwUndoStart(), cmwUndoDone();
/*
* A single undo event for the
* color map module.
@ -51,15 +57,7 @@ UndoType cmwUndoClientID;
* of an undo/redo command.
*/
bool cmwColorsChanged[256];
/*
* Functions to play events forward/backward.
*/
void cmwUndoForw(colorUE *up);
void cmwUndoBack(colorUE *up);
void cmwUndoStart(void);
void cmwUndoDone(void);
/*
* ----------------------------------------------------------------------------
*
@ -79,13 +77,13 @@ void cmwUndoDone(void);
*/
void
CMWundoInit(void)
CMWundoInit()
{
cmwUndoClientID = UndoAddClient(cmwUndoStart, cmwUndoDone, NULL, NULL,
cmwUndoForw, cmwUndoBack, "color map");
}
/*
* ----------------------------------------------------------------------------
*
@ -104,21 +102,21 @@ CMWundoInit(void)
*/
void
cmwUndoForw(
colorUE *up)
cmwUndoForw(up)
colorUE *up;
{
(void) GrPutColor(up->cue_color, up->new_r, up->new_g, up->new_b);
cmwColorsChanged[up->cue_color] = TRUE;
}
void
cmwUndoBack(
colorUE *up)
cmwUndoBack(up)
colorUE *up;
{
(void) GrPutColor(up->cue_color, up->old_r, up->old_g, up->old_b);
cmwColorsChanged[up->cue_color] = TRUE;
}
/*
* ----------------------------------------------------------------------------
*
@ -136,14 +134,10 @@ cmwUndoBack(
*/
void
cmwUndoColor(
int color,
int oldr,
int oldg,
int oldb,
int newr,
int newg,
int newb)
cmwUndoColor(color, oldr, oldg, oldb, newr, newg, newb)
int color;
int oldr, oldg, oldb;
int newr, newg, newb;
{
colorUE *up;
@ -159,7 +153,7 @@ cmwUndoColor(
up->new_g = newg;
up->new_b = newb;
}
/*
* ----------------------------------------------------------------------------
*
@ -177,14 +171,14 @@ cmwUndoColor(
*/
void
cmwUndoStart(void)
cmwUndoStart()
{
int i;
for (i = 0; i < 256; i++)
cmwColorsChanged[i] = FALSE;
}
/*
* ----------------------------------------------------------------------------
*
@ -204,13 +198,13 @@ cmwUndoStart(void)
*/
void
cmwUndoDone(void)
cmwUndoDone()
{
int i;
extern int cmwRedisplayFunc(MagWindow *w, int color);
extern int cmwRedisplayFunc();
for (i = 0; i < 256; i++)
if (cmwColorsChanged[i])
(void) WindSearch(CMWclientID, (ClientData) NULL, (Rect *) NULL,
cmwRedisplayFunc, INT2CD(i));
cmwRedisplayFunc, (ClientData) i);
}

16
cmwind/Depend Normal file
View File

@ -0,0 +1,16 @@
CMWmain.o: CMWmain.c ../utils/magic.h ../utils/geometry.h \
../windows/windows.h ../database/database.h ../tiles/tile.h \
../utils/hash.h ../utils/main.h ../commands/commands.h \
../cmwind/cmwind.h ../textio/txcommands.h ../graphics/graphicsInt.h \
../graphics/graphics.h ../textio/textio.h ../utils/utils.h \
../utils/styles.h ../graphics/glyphs.h ../utils/malloc.h
CMWcmmnds.o: CMWcmmnds.c ../tcltk/tclmagic.h ../utils/magic.h \
../utils/geometry.h ../windows/windows.h ../tiles/tile.h ../utils/hash.h \
../database/database.h ../dbwind/dbwind.h ../utils/main.h \
../commands/commands.h ../cmwind/cmwind.h ../textio/txcommands.h \
../graphics/graphics.h ../textio/textio.h ../utils/utils.h \
../utils/styles.h ../utils/undo.h
CMWundo.o: CMWundo.c ../utils/magic.h ../utils/geometry.h \
../graphics/graphics.h ../windows/windows.h ../cmwind/cmwind.h \
../textio/txcommands.h ../utils/undo.h
CMWrgbhsv.o: CMWrgbhsv.c ../utils/magic.h

View File

@ -4,23 +4,23 @@
* Interface definitions for the 'glue' between the window
* manager and the color map editor.
*
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
*
* rcsid $Header: /usr/cvsroot/magic-8.0/cmwind/cmwind.h,v 1.2 2009/09/10 20:32:51 tim Exp $
*/
#ifndef _MAGIC__CMWIND__CMWIND_H
#define _MAGIC__CMWIND__CMWIND_H
#ifndef _CMWIND_H
#define _CMWIND_H
#include "windows/windows.h"
#include "textio/txcommands.h"
@ -69,16 +69,12 @@ typedef struct
extern void CMWloadWindow(MagWindow *, int);
extern void CMWcommand(MagWindow *, TxCommand *);
extern const Rect colorWindowRect;
extern Rect colorWindowRect;
extern WindClient CMWclientID;
extern const ColorBar colorBars[];
extern const ColorPump colorPumps[];
extern const Rect cmwCurrentColorArea;
extern ColorBar colorBars[];
extern ColorPump colorPumps[];
extern Rect cmwCurrentColorArea;
extern void cmwUndoColor(int, int, int, int, int, int, int);
extern bool CMWCheckWritten(void);
/* C99 compat */
extern void CMWinit(void);
#endif /* _MAGIC__CMWIND__CMWIND_H */
#endif /* _CMWIND_H */

View File

@ -3,21 +3,21 @@
*
* Commands with names beginning with the letters A through B.
*
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
*/
#ifndef lint
static const char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magic-8.0/commands/CmdAB.c,v 1.1.1.1 2008/02/03 20:43:50 tim Exp $";
static char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magic-8.0/commands/CmdAB.c,v 1.1.1.1 2008/02/03 20:43:50 tim Exp $";
#endif /* not lint */
#include <stdio.h>
@ -44,13 +44,13 @@ static const char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magi
#include "utils/netlist.h"
#include "select/select.h"
/* ---------------------------------------------------------------------------
*
* CmdAddPath --
*
* Implement the "addpath" command: append to the global cell search path.
* (Usage superseded by extended "path" command; retained for compatibility)
* (Usage superceded by extended "path" command; retained for compatibility)
*
* Usage:
* addpath path
@ -70,9 +70,9 @@ static const char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magi
/*ARGSUSED*/
void
CmdAddPath(
MagWindow *w,
TxCommand *cmd)
CmdAddPath( w, cmd )
MagWindow *w;
TxCommand *cmd;
{
if (cmd->tx_argc != 2) {
TxError("Usage: %s appended_search_path\n", cmd->tx_argv[0]);
@ -80,71 +80,7 @@ CmdAddPath(
}
PaAppend(&Path, cmd->tx_argv[1]);
}
/*
* ----------------------------------------------------------------------------
*
* CmdArchive --
*
* Save an entire database to a "crash recovery"-type archive file, or
* load a database from a "crash recovery"-type archive file. Option
* "writeall" writes everything, including read-only PDK cells, while
* "readref" does not dereference and will prefer files found in the
* search path over content in the archive.
*
*
* Usage:
* archive write|writeall|read|readref file
*
* Results:
* None.
*
* Side effects:
* Writes a single file with the contents of the entire database,
* or loads the database with multiple cells from the file.
*
* ----------------------------------------------------------------------------
*/
void
CmdArchive(
MagWindow *w,
TxCommand *cmd)
{
int option = -1;
char *filename = NULL;
static const char * const cmdArchiveOpt[] = {"write", "writeall",
"read", "readref", 0};
if (cmd->tx_argc != 3)
TxError("Usage: %s write|writeall|read|readref filename\n", cmd->tx_argv[0]);
else
{
option = Lookup(cmd->tx_argv[1], cmdArchiveOpt);
if (option < 0)
{
TxError("Usage: %s write|writeall|read|readref filename\n", cmd->tx_argv[0]);
return;
}
}
filename = cmd->tx_argv[2];
switch(option) {
case 0: /* write */
DBWriteBackup(filename, TRUE, FALSE);
break;
case 1: /* writeall */
DBWriteBackup(filename, TRUE, TRUE);
break;
case 2: /* read */
DBReadBackup(filename, TRUE, TRUE);
break;
case 3: /* readref */
DBReadBackup(filename, TRUE, FALSE);
break;
}
}
/* Linked-list structure for returning information about arrayed cells */
@ -194,11 +130,11 @@ typedef struct LA1
#define ARRAY_DEFAULT 6
void
CmdArray(
MagWindow *w,
TxCommand *cmd)
CmdArray(w, cmd)
MagWindow *w;
TxCommand *cmd;
{
static const char * const cmdArrayOption[] = {
static char *cmdArrayOption[] = {
"count [[xlo] xhi [ylo] yhi] array subcells",
"width [value] set or return array x-spacing",
"height [value] set or return array y-spacing",
@ -208,7 +144,7 @@ CmdArray(
NULL
};
const char * const *msg;
char **msg;
int option, locargc, argstart;
bool doList = FALSE;
ArrayInfo a;
@ -220,7 +156,7 @@ CmdArray(
Tcl_Obj *tobj;
#endif
extern int selGetArrayFunc(CellUse *selUse, CellUse *use, Transform *trans, LinkedArray **arg);
extern int selGetArrayFunc();
locargc = cmd->tx_argc;
argstart = 1;
@ -237,7 +173,7 @@ CmdArray(
}
if (locargc <= 1)
goto badusage; /* Prohibits "array -list" alone */
option = Lookup(cmd->tx_argv[argstart], cmdArrayOption);
if (option < 0) {
if (locargc == 3 || locargc == 5)
@ -250,7 +186,7 @@ CmdArray(
/* Get all information about cell uses in the current selection */
(void) SelEnumCells(FALSE, (bool *) NULL, (SearchContext *) NULL,
(void) SelEnumCells(FALSE, (bool *) NULL, (SearchContext *) NULL,
selGetArrayFunc, (ClientData) &lahead);
/* Note: All "unimplemented functions" below will require a routine
@ -304,7 +240,7 @@ CmdArray(
goto badusage;
if (!StrIsInt(cmd->tx_argv[argstart + 1])
|| !StrIsInt(cmd->tx_argv[argstart + 2]))
|| !StrIsInt(cmd->tx_argv[argstart + 2]))
goto badusage;
if (locargc == 4)
@ -317,7 +253,7 @@ CmdArray(
}
else if (locargc == 6)
{
if (!StrIsInt(cmd->tx_argv[argstart + 3]) ||
if (!StrIsInt(cmd->tx_argv[argstart + 3]) ||
!StrIsInt(cmd->tx_argv[argstart + 4])) goto badusage;
a.ar_xlo = atoi(cmd->tx_argv[argstart + 1]);
a.ar_xhi = atoi(cmd->tx_argv[argstart + 2]);
@ -490,7 +426,7 @@ CmdArray(
case ARRAY_DEFAULT:
if (!StrIsInt(cmd->tx_argv[argstart])
|| !StrIsInt(cmd->tx_argv[argstart + 1]))
|| !StrIsInt(cmd->tx_argv[argstart + 1]))
goto badusage;
if (locargc == 3)
{
@ -502,7 +438,7 @@ CmdArray(
}
else
{
if (!StrIsInt(cmd->tx_argv[argstart + 2]) ||
if (!StrIsInt(cmd->tx_argv[argstart + 2]) ||
!StrIsInt(cmd->tx_argv[argstart + 3])) goto badusage;
a.ar_xlo = atoi(cmd->tx_argv[argstart]);
a.ar_xhi = atoi(cmd->tx_argv[argstart + 1]);
@ -530,15 +466,11 @@ badusage:
}
freelist:
la = lahead;
while (la != NULL)
{
la = lahead;
while (la != NULL)
{
free_magic1_t mm1 = freeMagic1_init();
freeMagic1(&mm1, (char *)la);
la = la->ar_next;
freeMagic1_end(&mm1);
}
freeMagic((char *)la);
la = la->ar_next;
}
return;
}
@ -548,14 +480,14 @@ freelist:
*/
int
selGetArrayFunc(
CellUse *selUse,
CellUse *use,
Transform *trans,
LinkedArray **arg)
selGetArrayFunc(selUse, use, trans, arg)
CellUse *selUse;
CellUse *use;
Transform *trans;
LinkedArray **arg;
{
/* Check "use" for array information and pass this to arrayInfo */
LinkedArray *la;
int xlo, xhi, ylo, yhi, xsep, ysep, t;
@ -578,17 +510,17 @@ selGetArrayFunc(
la->arrayInfo.ar_xhi = xhi;
la->arrayInfo.ar_ylo = ylo;
la->arrayInfo.ar_yhi = yhi;
/* Reverse the transformation in DBMakeArray */
ysep = (trans->t_d * use->cu_xsep - trans->t_a * use->cu_ysep);
ysep /= (trans->t_d * trans->t_b - trans->t_a * trans->t_e);
if (trans->t_a == 0)
xsep = (use->cu_ysep - trans->t_e * ysep) / trans->t_d;
else
xsep = (use->cu_xsep - trans->t_b * ysep) / trans->t_a;
la->arrayInfo.ar_xsep = xsep;
la->arrayInfo.ar_ysep = ysep;
@ -599,7 +531,7 @@ selGetArrayFunc(
return 0;
}
/*
* ----------------------------------------------------------------------------
*
@ -613,8 +545,6 @@ selGetArrayFunc(
* box size [width height]
* box position [llx lly] [-edit]
* box values [llx lly urx ury] [-edit]
* box remove
* box select
*
* box <direction> <distance> | cursor
*
@ -650,29 +580,25 @@ selGetArrayFunc(
#define BOX_SIZE 2
#define BOX_POSITION 3
#define BOX_VALUES 4
#define BOX_REMOVE 5
#define BOX_SELECT 6
#define BOX_MOVE 7
#define BOX_GROW 8
#define BOX_SHRINK 9
#define BOX_CORNER 10
#define BOX_EXISTS 11
#define BOX_HELP 12
#define BOX_DEFAULT 13
#define BOX_MOVE 5
#define BOX_GROW 6
#define BOX_SHRINK 7
#define BOX_CORNER 8
#define BOX_EXISTS 9
#define BOX_HELP 10
#define BOX_DEFAULT 11
void
CmdBox(
MagWindow *w,
TxCommand *cmd)
CmdBox(w, cmd)
MagWindow *w;
TxCommand *cmd;
{
static const char * const cmdBoxOption[] = {
static char *cmdBoxOption[] = {
"width [value] set or return box width",
"height [value] set or return box height",
"size [width height] set or return box size",
"position [llx lly] [-edit] set or return box position",
"values [llx lly urx ury] [-edit] set or return box coordinates",
"remove remove cursor box from display",
"select set box to selection bounding box",
"move <direction> <distance> move box position",
"grow <direction> <distance> expand box size",
"shrink <direction> <distance> shrink box size",
@ -683,7 +609,7 @@ CmdBox(
};
CellDef *rootBoxDef;
Rect rootBox, editbox, savebox, *boxptr;
Rect rootBox, editbox, *boxptr;
Point ll;
int option, direction, distancex, distancey;
int width, height;
@ -694,7 +620,7 @@ CmdBox(
bool needBox = TRUE; /* require that box be defined */
bool refEdit = FALSE; /* referenced to edit cell coordinates */
bool cursorRef = FALSE; /* reference position is the cursor */
const char * const *msg;
char **msg;
argc = cmd->tx_argc;
if (argc > 7) goto badusage;
@ -732,12 +658,6 @@ CmdBox(
windCheckOnlyWindow(&w, DBWclientID);
if (option == BOX_REMOVE)
{
DBWSetBox((CellDef *)NULL, &GeoNullRect);
return;
}
/*----------------------------------------------------------*/
/* Check for the command options which do not require a box */
/* to be present. */
@ -770,7 +690,7 @@ CmdBox(
#endif
return;
}
if (needBox)
{
if (refEdit)
@ -824,7 +744,6 @@ CmdBox(
/*----------------------------------------------------------*/
boxptr = (refEdit) ? &editbox : &rootBox;
savebox = *boxptr;
/*----------------------------------------------------------*/
/* Parse arguments according to class */
@ -865,13 +784,6 @@ CmdBox(
ToolMoveCorner(tcorner, &cmd->tx_p, TRUE, rootBoxDef);
break;
}
/* Recast command as "box values" for logging purposes */
ToolGetBox(&rootBoxDef, &rootBox);
sprintf(cmd->tx_argstring, "box values %di %di %di %di",
rootBox.r_xbot, rootBox.r_ybot,
rootBox.r_xtop, rootBox.r_ytop);
TxRebuildCommand(cmd);
return;
}
else if (DBWSnapToGrid != DBW_SNAP_USER)
@ -995,19 +907,6 @@ CmdBox(
boxptr->r_ytop = boxptr->r_ybot + height;
break;
case BOX_SELECT:
if (argc == 2)
{
Rect selarea;
GeoTransRect(&SelectUse->cu_transform, &SelectDef->cd_bbox, &selarea);
boxptr->r_xbot = selarea.r_xbot;
boxptr->r_ybot = selarea.r_ybot;
boxptr->r_xtop = selarea.r_xtop;
boxptr->r_ytop = selarea.r_ytop;
}
else goto badusage;
break;
case BOX_VALUES:
if (argc == 2)
{
@ -1194,13 +1093,13 @@ CmdBox(
if (area > 0)
TxPrintf(" area (units^2)");
TxPrintf("\n\nmicrons: %6.3f x %-6.3f (% 6.3f, % -6.3f), "
"(% 6.3f, % -6.3f)",
TxPrintf("\n\nmicrons: %6.2f x %-6.2f (% 6.2f, % -6.2f), "
"(% 6.2f, % -6.2f)",
(float)width *oscale, (float)height * oscale,
(float)boxptr->r_xbot * oscale, (float)boxptr->r_ybot * oscale,
(float)boxptr->r_xtop * oscale, (float)boxptr->r_ytop * oscale);
if (area > 0)
TxPrintf(" %-10.3f", (float)area * oscale * oscale);
TxPrintf(" %-10.2f", (float)area * oscale * oscale);
TxPrintf("\nlambda:");
if (DBLambda[0] != DBLambda[1])
@ -1223,7 +1122,7 @@ CmdBox(
boxptr->r_xbot, boxptr->r_ybot,
boxptr->r_xtop, boxptr->r_ytop);
if (area > 0)
TxPrintf(" %-10"DLONG_PREFIX"d", area);
TxPrintf(" %-10lld", area);
TxPrintf("\n");
break;
@ -1243,18 +1142,6 @@ badusage:
if (refEdit)
GeoTransRect(&EditToRootTransform, &editbox, &rootBox);
/*----------------------------------------------------------*/
/* Check for numerical overflow in box values */
/*----------------------------------------------------------*/
if (boxptr->r_ll.p_x < (MINFINITY + 2) || boxptr->r_ll.p_x > (INFINITY - 2) ||
boxptr->r_ll.p_y < (MINFINITY + 2) || boxptr->r_ll.p_y > (INFINITY - 2))
{
*boxptr = savebox;
TxError("Box out of bounds.\n");
return;
}
/*----------------------------------------------------------*/
/* Change the position of the box in the layout window */
/*----------------------------------------------------------*/

View File

@ -5,16 +5,16 @@
* functions which have been compiled as Tcl modules, using the Tcl
* interface.
*
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
*/
@ -48,9 +48,9 @@
*/
void
CmdAutoExtToSim(
MagWindow *w,
TxCommand *cmd)
CmdAutoExtToSim(w, cmd)
MagWindow *w;
TxCommand *cmd;
{
int result;
@ -83,9 +83,9 @@ CmdAutoExtToSim(
*/
void
CmdAutoExtToSpice(
MagWindow *w,
TxCommand *cmd)
CmdAutoExtToSpice(w, cmd)
MagWindow *w;
TxCommand *cmd;
{
int result;
@ -119,9 +119,9 @@ CmdAutoExtToSpice(
*/
void
CmdAutoRoute(
MagWindow *w,
TxCommand *cmd)
CmdAutoRoute(w, cmd)
MagWindow *w;
TxCommand *cmd;
{
int result;
@ -154,9 +154,9 @@ CmdAutoRoute(
*/
void
CmdAutoPlot(
MagWindow *w,
TxCommand *cmd)
CmdAutoPlot(w, cmd)
MagWindow *w;
TxCommand *cmd;
{
int result;
@ -189,9 +189,9 @@ CmdAutoPlot(
*/
void
CmdAutoLef(
MagWindow *w,
TxCommand *cmd)
CmdAutoLef(w, cmd)
MagWindow *w;
TxCommand *cmd;
{
int result;

File diff suppressed because it is too large Load Diff

View File

@ -3,21 +3,21 @@
*
* Commands with names beginning with the letter E.
*
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
*/
#ifndef lint
static const char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magic-8.0/commands/CmdE.c,v 1.4 2010/06/17 14:38:33 tim Exp $";
static char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magic-8.0/commands/CmdE.c,v 1.4 2010/06/17 14:38:33 tim Exp $";
#endif /* not lint */
#include <stdio.h>
@ -42,13 +42,9 @@ static const char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magi
#include "drc/drc.h"
#include "textio/txcommands.h"
#include "extract/extract.h"
#include "extract/extractInt.h"
#include "select/select.h"
/* C99 compat */
#include "dbwind/dbwtech.h"
/*
* ----------------------------------------------------------------------------
*
@ -56,12 +52,10 @@ static const char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magi
*
* Implement the "edit" command.
* Use the cell that is currently selected as the edit cell. If more than
* one cell is selected, use the point to choose between them. If the
* optional argument "<instname>" is provided, then edit the specified
* instance (if it exists in the current layout window).
* one cell is selected, use the point to choose between them.
*
* Usage:
* edit [<instname>]
* edit
*
* Results:
* None.
@ -79,29 +73,18 @@ static const char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magi
static bool cmdFoundNewEdit;
void
CmdEdit(
MagWindow *w,
TxCommand *cmd)
CmdEdit(w, cmd)
MagWindow *w;
TxCommand *cmd;
{
Rect area, pointArea;
CellUse *usave, *use = NULL;
CellUse *usave;
CellDef *csave;
int cmdEditRedisplayFunc(MagWindow *w, Rect *area); /* Forward declaration. */
int cmdEditEnumFunc(CellUse *selUse, CellUse *use, Transform *transform, Rect *area); /* Forward declaration. */
int cmdEditRedisplayFunc(); /* Forward declaration. */
int cmdEditEnumFunc(); /* Forward declaration. */
bool noCurrentUse = FALSE;
if ((w != NULL) && (cmd->tx_argc == 2))
{
CellUse *rootUse;
SearchContext scx;
rootUse = (CellUse *)w->w_surfaceID;
bzero(&scx, sizeof(SearchContext));
DBTreeFindUse(cmd->tx_argv[1], rootUse, &scx);
use = scx.scx_use;
}
if ((use == NULL) && (cmd->tx_argc > 1))
if (cmd->tx_argc > 1)
{
TxError("Usage: edit\nMaybe you want the \"load\" command\n");
return;
@ -115,7 +98,7 @@ CmdEdit(
* only in windows where the edit cell is displayed differently from
* other cells.
*/
GeoTransRect(&EditToRootTransform, &(usave->cu_def->cd_bbox), &area);
(void) WindSearch(DBWclientID, (ClientData) NULL,
(Rect *) NULL, cmdEditRedisplayFunc, (ClientData) &area);
@ -123,29 +106,21 @@ CmdEdit(
DBWUndoOldEdit(EditCellUse, EditRootDef, &EditToRootTransform,
&RootToEditTransform);
}
/* Use the position of the point to select one of the currently-selected
* cells (if there are more than one). If worst comes to worst, just
* select any selected cell.
*/
(void) ToolGetPoint((Point *) NULL, &pointArea);
cmdFoundNewEdit = FALSE;
csave = EditRootDef;
usave = EditCellUse;
EditCellUse = NULL;
if (use == NULL)
{
EditCellUse = NULL;
SelEnumCells(FALSE, (bool *) NULL, (SearchContext *) NULL,
cmdEditEnumFunc, (ClientData) &pointArea);
}
else
{
EditCellUse = use;
cmdFoundNewEdit = TRUE;
}
(void) SelEnumCells(FALSE, (bool *) NULL, (SearchContext *) NULL,
cmdEditEnumFunc, (ClientData) &pointArea);
if (EditCellUse == (CellUse *)NULL)
{
@ -155,7 +130,7 @@ CmdEdit(
return;
}
else if (!(EditCellUse->cu_def->cd_flags & CDAVAILABLE))
DBCellRead(EditCellUse->cu_def, TRUE, TRUE, NULL);
DBCellRead(EditCellUse->cu_def, (char *)NULL, TRUE, NULL);
if (EditCellUse->cu_def->cd_flags & CDNOEDIT)
{
@ -179,14 +154,6 @@ CmdEdit(
GeoTransRect(&EditToRootTransform, &(EditCellUse->cu_def->cd_bbox), &area);
(void) WindSearch(DBWclientID, (ClientData) NULL,
(Rect *) NULL, cmdEditRedisplayFunc, (ClientData) &area);
if ((cmd->tx_argc == 1) && cmdFoundNewEdit)
{
/* Recast the command with the instance name for logging */
sprintf(cmd->tx_argstring, "edit %s", EditCellUse->cu_id);
TxRebuildCommand(cmd);
}
}
/* Search function to handle redisplays for CmdEdit: it checks to
@ -197,11 +164,11 @@ CmdEdit(
*/
int
cmdEditRedisplayFunc(
MagWindow *w, /* Window containing edit cell. */
Rect *area) /* Area to be redisplayed. */
cmdEditRedisplayFunc(w, area)
MagWindow *w; /* Window containing edit cell. */
Rect *area; /* Area to be redisplayed. */
{
static const Rect origin = {{-1, -1}, {1, 1}};
static Rect origin = {-1, -1, 1, 1};
Rect tmp;
DBWclientRec *crec = (DBWclientRec *) w->w_clientData;
@ -226,13 +193,13 @@ cmdEditRedisplayFunc(
*/
int
cmdEditEnumFunc(
CellUse *selUse, /* Use from selection (not used). */
CellUse *use, /* Use from layout that corresponds to
cmdEditEnumFunc(selUse, use, transform, area)
CellUse *selUse; /* Use from selection (not used). */
CellUse *use; /* Use from layout that corresponds to
* selUse (could be an array!).
*/
Transform *transform, /* Transform from use->cu_def to root coords. */
Rect *area) /* We're looking for a use containing this
Transform *transform; /* Transform from use->cu_def to root coords. */
Rect *area; /* We're looking for a use containing this
* area, in root coords.
*/
{
@ -260,7 +227,7 @@ cmdEditEnumFunc(
/* It overlaps. Now find out which array element it points to,
* and adjust the transforms accordingly.
*/
DBArrayOverlap(use, &useArea, &xlo, &xhi, &ylo, &yhi);
GeoTransTrans(DBGetArrayTransform(use, xlo, ylo), transform,
&EditToRootTransform);
@ -305,20 +272,20 @@ cmdEditEnumFunc(
#define OPTION_FLAGS 3
void
CmdElement(
MagWindow *w,
TxCommand *cmd)
CmdElement(w, cmd)
MagWindow *w;
TxCommand *cmd;
{
int option, type;
const char * const *msg;
char **msg;
Rect area;
int style;
CellDef *def;
CellUse *use;
bool getopt;
static const char * const cmdElementOption[] = {
static char *cmdElementOption[] = {
"add create a new element",
"delete delete an existing element",
"configure configure or query an existing element",
@ -328,14 +295,14 @@ CmdElement(
NULL
};
static const char * const cmdElementType[] = {
static char *cmdElementType[] = {
"line name style x1 y1 x2 y2",
"rectangle name style llx lly urx ury",
"text name style cx cy label",
NULL
};
static const char * const cmdConfigureType[] = {
static char *cmdConfigureType[] = {
"text get (or) replace <string>",
"style get (or) add <style> (or) remove <style>",
"position get (or) <point> (or) <rect>",
@ -390,8 +357,10 @@ CmdElement(
return;
}
}
area.r_xbot = cmdParseCoord(w, cmd->tx_argv[5], FALSE, TRUE);
area.r_ybot = cmdParseCoord(w, cmd->tx_argv[6], FALSE, FALSE);
if (!StrIsInt(cmd->tx_argv[5])) goto badusage;
area.r_xbot = atoi(cmd->tx_argv[5]);
if (!StrIsInt(cmd->tx_argv[6])) goto badusage;
area.r_ybot = atoi(cmd->tx_argv[6]);
switch (type)
{
@ -402,8 +371,10 @@ CmdElement(
cmdElementType[ELEMENT_LINE]);
return;
}
area.r_xtop = cmdParseCoord(w, cmd->tx_argv[7], FALSE, TRUE);
area.r_ytop = cmdParseCoord(w, cmd->tx_argv[8], FALSE, FALSE);
if (!StrIsInt(cmd->tx_argv[7])) goto badusage;
area.r_xtop = atoi(cmd->tx_argv[7]);
if (!StrIsInt(cmd->tx_argv[8])) goto badusage;
area.r_ytop = atoi(cmd->tx_argv[8]);
DBWElementAddLine(w, cmd->tx_argv[3], &area, def, style);
break;
case ELEMENT_RECT:
@ -413,8 +384,10 @@ CmdElement(
cmdElementType[ELEMENT_RECT]);
return;
}
area.r_xtop = cmdParseCoord(w, cmd->tx_argv[7], FALSE, TRUE);
area.r_ytop = cmdParseCoord(w, cmd->tx_argv[8], FALSE, FALSE);
if (!StrIsInt(cmd->tx_argv[7])) goto badusage;
area.r_xtop = atoi(cmd->tx_argv[7]);
if (!StrIsInt(cmd->tx_argv[8])) goto badusage;
area.r_ytop = atoi(cmd->tx_argv[8]);
DBWElementAddRect(w, cmd->tx_argv[3], &area, def, style);
break;
case ELEMENT_TEXT:
@ -528,19 +501,21 @@ CmdElement(
if (cmd->tx_argc >= 6)
{
crect.r_xbot = cmdParseCoord(w, cmd->tx_argv[4],
FALSE, TRUE);
crect.r_ybot = cmdParseCoord(w, cmd->tx_argv[5],
FALSE, FALSE);
if (!StrIsInt(cmd->tx_argv[4]) ||
!StrIsInt(cmd->tx_argv[5]))
goto badrect;
crect.r_xbot = atoi(cmd->tx_argv[4]);
crect.r_ybot = atoi(cmd->tx_argv[5]);
crect.r_xtop = crect.r_xbot; /* placeholder */
crect.r_ytop = crect.r_ybot; /* placeholder */
}
if (cmd->tx_argc == 8)
{
crect.r_xtop = cmdParseCoord(w, cmd->tx_argv[6],
FALSE, TRUE);
crect.r_ytop = cmdParseCoord(w, cmd->tx_argv[7],
FALSE, FALSE);
if (!StrIsInt(cmd->tx_argv[6]) ||
!StrIsInt(cmd->tx_argv[7]))
goto badrect;
crect.r_xtop = atoi(cmd->tx_argv[6]);
crect.r_ytop = atoi(cmd->tx_argv[7]);
}
if (cmd->tx_argc == 6 || cmd->tx_argc == 8)
@ -595,7 +570,7 @@ badusage:
}
/*
* ----------------------------------------------------------------------------
*
@ -606,7 +581,7 @@ badusage:
* EditCellUse->cu_def.
*
* Usage:
* erase [layers | cursor | pick x y]
* erase [layers | cursor]
*
* Results:
* None.
@ -627,39 +602,24 @@ static CellUse *cmdEraseCells[MAXCELLS];
static int cmdEraseCount;
void
CmdErase(
MagWindow *w,
TxCommand *cmd)
CmdErase(w, cmd)
MagWindow *w;
TxCommand *cmd;
{
Rect editRect, areaReturn;
TileTypeBitMask mask, errorLayersForErasure, activeLayersForErasure;
extern int cmdEraseCellsFunc(SearchContext *scx, ClientData cdarg);
extern int cmdEraseCellsFunc();
windCheckOnlyWindow(&w, DBWclientID);
if (w == (MagWindow *) NULL) return;
if ((cmd->tx_argc == 4) && !strcmp(cmd->tx_argv[1], "pick"))
{
Point editPoint, rootPoint;
editPoint.p_x = cmdParseCoord(w, cmd->tx_argv[2], FALSE, TRUE);
editPoint.p_y = cmdParseCoord(w, cmd->tx_argv[3], FALSE, FALSE);
GeoTransPoint(&EditToRootTransform, &editPoint, &rootPoint);
CmdPaintEraseButton(w, &rootPoint, FALSE, FALSE);
return;
}
if (cmd->tx_argc > 2)
{
TxError("Usage: %s [<layers> | cursor | pick x y]\n", cmd->tx_argv[0]);
TxError("Usage: %s [<layers> | cursor]\n", cmd->tx_argv[0]);
return;
}
if (!ToolGetEditBox(&editRect)) return;
if (EditCellUse == NULL)
{
TxError("No cell def being edited!\n");
return;
}
/*
* Erase with no arguments is the same as erasing
@ -671,16 +631,7 @@ CmdErase(
(void) CmdParseLayers("*,label", &mask);
else if (!strncmp(cmd->tx_argv[1], "cursor", 6))
{
Point editPoint, rootPoint;
CmdPaintEraseButton(w, &cmd->tx_p, FALSE, TRUE);
/* Recast the command as "erase pick x y" for logging purposes */
CmdGetRootPoint(&rootPoint, (Rect *)NULL);
GeoTransPoint(&RootToEditTransform, &rootPoint, &editPoint);
sprintf(cmd->tx_argstring, "erase pick %di %di", editPoint.p_x,
editPoint.p_y);
TxRebuildCommand(cmd);
CmdPaintEraseButton(w, &cmd->tx_p, FALSE);
return;
}
else if (!CmdParseLayers(cmd->tx_argv[1], &mask))
@ -723,7 +674,7 @@ CmdErase(
* area of interest, then erase all those cells. Continue
* this until all cells have been erased.
*/
scx.scx_use = EditCellUse;
scx.scx_x = scx.scx_y = 0;
scx.scx_area = editRect;
@ -759,20 +710,20 @@ CmdErase(
}
int
cmdEraseCellsFunc(
SearchContext *scx, /* Indicates cell found. */
ClientData cdarg) /* Not used. */
cmdEraseCellsFunc(scx, cdarg)
SearchContext *scx; /* Indicates cell found. */
ClientData cdarg; /* Not used. */
{
/* All this procedure does is to remember cells that are
* found, up to MAXCELLS of them.
*/
if (cmdEraseCount >= MAXCELLS) return 1;
cmdEraseCells[cmdEraseCount] = scx->scx_use;
cmdEraseCount += 1;
return 2;
}
/*
* ----------------------------------------------------------------------------
*
@ -797,17 +748,17 @@ cmdEraseCellsFunc(
*/
void
CmdExpand(
MagWindow *w,
TxCommand *cmd)
CmdExpand(w, cmd)
MagWindow *w;
TxCommand *cmd;
{
int windowMask, boxMask, d;
Rect rootRect;
CellUse *rootBoxUse;
CellDef *rootBoxDef;
int cmdExpandFunc(CellUse *use, int windowMask); /* Forward reference. */
int cmdExpandFunc(); /* Forward reference. */
if (cmd->tx_argc > 2 || (cmd->tx_argc == 2
if (cmd->tx_argc > 2 || (cmd->tx_argc == 2
&& (strncmp(cmd->tx_argv[1], "toggle", strlen(cmd->tx_argv[1])) != 0)))
{
TxError("Usage: %s or %s toggle\n", cmd->tx_argv[0], cmd->tx_argv[0]);
@ -829,7 +780,7 @@ CmdExpand(
/* the cursor box and window to restore the original view. */
d = DBLambda[1];
do
do
{
if (d != DBLambda[1])
{
@ -869,16 +820,16 @@ CmdExpand(
*/
int
cmdExpandFunc(
CellUse *use, /* Use that was just expanded. */
int windowMask) /* Window where it was expanded. */
cmdExpandFunc(use, windowMask)
CellUse *use; /* Use that was just expanded. */
int windowMask; /* Window where it was expanded. */
{
if (use->cu_parent == NULL) return 0;
DBWAreaChanged(use->cu_parent, &use->cu_bbox, windowMask,
&DBAllButSpaceBits);
return 0;
}
/*
* ----------------------------------------------------------------------------
*
@ -904,17 +855,14 @@ cmdExpandFunc(
#define EXTALL 0
#define EXTCELL 1
#define EXTDO 2
#define EXTHALO 3
#define EXTHELP 4
#define EXTLENGTH 5
#define EXTNO 6
#define EXTPARENTS 7
#define EXTPATH 8
#define EXTSHOWPARENTS 9
#define EXTSTEPSIZE 10
#define EXTSTYLE 11
#define EXTUNIQUE 12
#define EXTWARN 13
#define EXTHELP 3
#define EXTLENGTH 4
#define EXTNO 5
#define EXTPARENTS 6
#define EXTSHOWPARENTS 7
#define EXTSTYLE 8
#define EXTUNIQUE 9
#define EXTWARN 10
#define WARNALL 0
#define WARNDUP 1
@ -926,10 +874,7 @@ cmdExpandFunc(
#define DOCAPACITANCE 2
#define DOCOUPLING 3
#define DOLENGTH 4
#define DOLOCAL 5
#define DORESISTANCE 6
#define DOLABELCHECK 7
#define DOALIASES 8
#define DORESISTANCE 5
#define LENCLEAR 0
#define LENDRIVER 1
@ -938,27 +883,23 @@ cmdExpandFunc(
#define UNIQALL 0
#define UNIQTAGGED 1
#define UNIQNOPORTS 2
#define UNIQNOTOPPORTS 3
void
CmdExtract(
MagWindow *w,
TxCommand *cmd)
CmdExtract(w, cmd)
MagWindow *w;
TxCommand *cmd;
{
const char * const *msg;
char *namep, *arg;
char **msg, *namep, *arg;
int option, warn, len, n, all;
int dist;
bool no;
CellUse *selectedUse;
CellDef *selectedDef;
bool dolist = FALSE;
bool doforall = FALSE;
bool doLocal = FALSE;
int argc = cmd->tx_argc;
char **argv = cmd->tx_argv;
static const char * const cmdExtWarn[] =
static char *cmdExtWarn[] =
{
"all enable all warnings",
"dup warn when different nodes have the same name",
@ -966,54 +907,44 @@ CmdExtract(
"labels warn when subcell nodes are unlabelled",
NULL
};
static const char * const cmdExtOption[] =
static char *cmdExtOption[] =
{
"adjust compensate R and C hierarchically",
"all all options",
"capacitance extract substrate capacitance",
"coupling extract coupling capacitance",
"length compute driver-receiver pathlengths",
"local put all generated files in the current directory",
"resistance estimate resistance",
"labelcheck check for connections through sticky labels",
"aliases output all net name aliases",
NULL
};
static const char * const cmdExtLength[] =
static char *cmdExtLength[] =
{
"clear clear the driver and receiver tables",
"driver termName(s) identify a driving (output) terminal",
"receiver termName(s) identify a receiving (input) terminal",
NULL
};
/* These must match definitions EXT_UNIQ_* in extract/extract.h: */
static const char * const cmdExtUniq[] =
static char *cmdExtUniq[] =
{
"all extract matching labels as unique nodes",
"# extract tagged labels as unique nodes",
"noports ignore ports when making labels unique",
"notopports ignore top-level ports when making labels unique",
NULL
};
static const char * const cmdExtCmd[] =
{
static char *cmdExtCmd[] =
{
"all extract root cell and all its children",
"cell name extract selected cell into file \"name\"",
"do [option] enable extractor option",
"halo [value] print or set the sidewall halo distance",
"help print this help information",
"length [option] control pathlength extraction information",
"no [option] disable extractor option",
"parents extract selected cell and all its parents",
"path [path] if set, extract into the indicated path",
"showparents show all parents of selected cell",
"stepsize [value] print or set the extraction step size",
"style [stylename] set current extraction parameter style",
"unique [option] generate unique names when different nodes\n\
have the same name",
"warn [ [no] option] enable/disable reporting of non-serious errors",
"warn [ [no] option] enable/disable reporting of non-fatal errors",
NULL
};
@ -1060,10 +991,7 @@ CmdExtract(
if (argc == 1)
{
if (!strcmp(selectedUse->cu_def->cd_name, UNNAMED))
TxError("Please name the cell before extracting.\n");
else
ExtIncremental(selectedUse);
ExtIncremental(selectedUse);
return;
}
}
@ -1094,10 +1022,7 @@ CmdExtract(
break;
case EXTALL:
if (!strcmp(selectedUse->cu_def->cd_name, UNNAMED))
TxError("Please name the cell before extracting.\n");
else
ExtAll(selectedUse);
ExtAll(selectedUse);
return;
case EXTCELL:
@ -1109,69 +1034,9 @@ CmdExtract(
TxError("No cell selected\n");
return;
}
ExtractOneCell(selectedUse->cu_def, namep, FALSE);
ExtCell(selectedUse->cu_def, namep, FALSE);
return;
case EXTHALO:
if (ExtCurStyle == NULL)
{
TxError("No extraction style set.\n");
return;
}
else if (argc == 2)
{
#ifdef MAGIC_WRAPPER
Tcl_Obj *tobj;
tobj = Tcl_NewIntObj(ExtCurStyle->exts_sideCoupleHalo);
Tcl_SetObjResult(magicinterp, tobj);
#else
TxPrintf("Side overlap halo is %d\n", ExtCurStyle->exts_sideCoupleHalo);
#endif
return;
}
else if (argc != 3) goto wrongNumArgs;
/* argv[2] is a halo distance */
dist = cmdParseCoord(w, argv[2], TRUE, TRUE);
if (dist < 0)
{
TxError("Bad halo distance. Halo must be non-negative.");
return;
}
else
ExtCurStyle->exts_sideCoupleHalo = dist;
break;
case EXTSTEPSIZE:
if (ExtCurStyle == NULL)
{
TxError("No extraction style set.\n");
return;
}
else if (argc == 2)
{
#ifdef MAGIC_WRAPPER
Tcl_Obj *tobj;
tobj = Tcl_NewIntObj(ExtCurStyle->exts_stepSize);
Tcl_SetObjResult(magicinterp, tobj);
#else
TxPrintf("Extraction step size is %d\n", ExtCurStyle->exts_stepSize);
#endif
return;
}
else if (argc != 3) goto wrongNumArgs;
/* argv[2] is a step size */
dist = cmdParseCoord(w, argv[2], TRUE, TRUE);
if (dist <= 0)
{
TxError("Bad step size. Step size must be strictly positive.");
return;
}
else
ExtCurStyle->exts_stepSize = dist;
break;
case EXTPARENTS:
selectedUse = CmdGetSelectedCell((Transform *) NULL);
if (selectedUse == NULL)
@ -1179,10 +1044,7 @@ CmdExtract(
TxError("No cell selected\n");
return;
}
if (!strcmp(selectedUse->cu_def->cd_name, UNNAMED))
TxError("Please name the cell before extracting.\n");
else
ExtParents(selectedUse);
ExtParents(selectedUse);
return;
case EXTSHOWPARENTS:
@ -1195,13 +1057,6 @@ CmdExtract(
ExtShowParents(selectedUse);
return;
case EXTPATH:
if (argc == 2)
ExtPrintPath(dolist);
else
ExtSetPath(argv[2]);
return;
case EXTSTYLE:
if (argc == 2)
ExtPrintStyle(dolist, doforall, !doforall);
@ -1278,8 +1133,6 @@ CmdExtract(
TxPrintf("%s coupling\n", OPTSET(EXT_DOCOUPLING));
TxPrintf("%s length\n", OPTSET(EXT_DOLENGTH));
TxPrintf("%s resistance\n", OPTSET(EXT_DORESISTANCE));
TxPrintf("%s label check\n", OPTSET(EXT_DOLABELCHECK));
TxPrintf("%s aliases\n", OPTSET(EXT_DOALIASES));
return;
#undef OPTSET
}
@ -1307,18 +1160,6 @@ CmdExtract(
case DOCOUPLING: option = EXT_DOCOUPLING; break;
case DOLENGTH: option = EXT_DOLENGTH; break;
case DORESISTANCE: option = EXT_DORESISTANCE; break;
case DOLABELCHECK: option = EXT_DOLABELCHECK; break;
case DOALIASES: option = EXT_DOALIASES; break;
case DOLOCAL:
/* "extract do local" and "extract no local" are kept for
* backwards compatibility, but now effectively implement
* "extract path ." and "extract path none", respectively.
*/
if (no)
StrDup(&ExtLocalPath, NULL);
else
StrDup(&ExtLocalPath, ".");
return;
}
if (no) ExtOptions &= ~option;
else ExtOptions |= option;

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

View File

@ -4,21 +4,21 @@
* The functions in this file are local to the commands module
* and not intended to be used by its clients.
*
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
*/
#ifndef lint
static const char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magic-8.0/commands/CmdSubrs.c,v 1.2 2010/06/24 12:37:15 tim Exp $";
static char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magic-8.0/commands/CmdSubrs.c,v 1.2 2010/06/24 12:37:15 tim Exp $";
#endif /* not lint */
#include <stdio.h>
@ -33,7 +33,6 @@ static const char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magi
#include "database/database.h"
#include "tiles/tile.h"
#include "utils/hash.h"
#include "utils/malloc.h"
#include "windows/windows.h"
#include "dbwind/dbwind.h"
#include "utils/main.h"
@ -52,9 +51,9 @@ static const char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magi
/* Forward declarations */
extern char *cmdCheckNewName(CellDef *def, char *newName, bool tryRename, bool noninteractive);
extern int cmdSaveWindSet(MagWindow *window, CellDef *def);
extern void CmdSetWindCaption(CellUse *newEditUse, CellDef *rootDef);
extern char *cmdCheckNewName();
extern int cmdSaveWindSet();
extern void CmdSetWindCaption();
TileTypeBitMask CmdYMLabel;
TileTypeBitMask CmdYMCell;
@ -100,12 +99,11 @@ TileTypeBitMask CmdYMAllButSpace;
*/
int
cmdScaleCoord(
MagWindow *w,
char *arg,
bool is_relative,
bool is_x,
int scale)
cmdScaleCoord(w, arg, is_relative, is_x, scale)
MagWindow *w;
char *arg;
bool is_relative, is_x;
int scale;
{
char *endptr;
double dval = 0;
@ -191,11 +189,6 @@ cmdScaleCoord(
return round(dval);
}
}
else if (!strcmp(endptr, "u"))
/* Maybe "u" is too ambiguous but it is very commonly used as
* an abbreviation for "micron".
*/
mscale = 1000;
else if (!strncmp(endptr, "micron", 6))
mscale = 1000;
else if (!strncmp(endptr, "centimicron", 11) || !strcmp(endptr, "cu"))
@ -207,8 +200,7 @@ cmdScaleCoord(
return round(dval);
}
}
if (!isspace(*endptr))
dval /= CIFGetOutputScale(mscale);
dval /= CIFGetOutputScale(mscale);
return round(dval);
}
@ -231,11 +223,10 @@ cmdScaleCoord(
*/
int
cmdParseCoord(
MagWindow *w,
char *arg,
bool is_relative,
bool is_x)
cmdParseCoord(w, arg, is_relative, is_x)
MagWindow *w;
char *arg;
bool is_relative, is_x;
{
return cmdScaleCoord(w, arg, is_relative, is_x, 1);
}
@ -259,7 +250,7 @@ cmdParseCoord(
*/
void
CmdInit(void)
CmdInit()
{
TTMaskZero(&CmdYMLabel);
TTMaskSetType(&CmdYMLabel, L_LABEL);
@ -270,7 +261,7 @@ CmdInit(void)
CmdYMAllButSpace = DBAllButSpaceBits;
TTMaskClearType(&CmdYMAllButSpace, L_CELL);
}
/*
* ----------------------------------------------------------------------------
*
@ -293,14 +284,11 @@ CmdInit(void)
*/
void
cmdFlushCell(
CellDef *def,
bool force_deref)
cmdFlushCell(def)
CellDef *def;
{
CellUse *parentUse;
if (def == NULL) return;
/* Disallow flushing a cell that contains the edit cell as a child */
if (EditCellUse && (EditCellUse->cu_parent == def))
{
@ -310,15 +298,6 @@ cmdFlushCell(
}
UndoFlush();
if (force_deref)
{
/* Force dereferencing */
def->cd_flags |= CDDEREFERENCE;
freeMagic(def->cd_file);
def->cd_file = NULL;
}
DBWAreaChanged(def, &def->cd_bbox, DBW_ALLWINDOWS,
(TileTypeBitMask *) NULL);
for (parentUse = def->cd_parents; parentUse != NULL;
@ -330,7 +309,7 @@ cmdFlushCell(
}
DBCellClearDef(def);
DBCellClearAvail(def);
(void) DBCellRead(def, TRUE, TRUE, NULL);
(void) DBCellRead(def, (char *) NULL, TRUE, NULL);
DBCellSetAvail(def);
DBReComputeBbox(def);
DBCellSetModified(def, FALSE);
@ -344,7 +323,7 @@ cmdFlushCell(
&parentUse->cu_bbox);
}
}
/*
* ----------------------------------------------------------------------------
*
@ -375,9 +354,9 @@ cmdFlushCell(
*/
bool
CmdParseLayers(
char *s,
TileTypeBitMask *mask)
CmdParseLayers(s, mask)
char *s;
TileTypeBitMask *mask;
{
TileTypeBitMask newmask, tempmask;
char *dp, c;
@ -396,23 +375,23 @@ CmdParseLayers(
#define LN_CONNECT 5
static struct
{
const char *layer_name;
char *layer_name;
int layer_value;
}
const special[] =
special[] =
{
{"$", LN_DOLLAR},
{"*", LN_ALL},
{"errors", LN_ERRORS},
{"labels", LN_LABELS},
{"subcell", LN_CELL},
{"connect", LN_CONNECT},
{0},
"$", LN_DOLLAR,
"*", LN_ALL,
"errors", LN_ERRORS,
"labels", LN_LABELS,
"subcell", LN_CELL,
"connect", LN_CONNECT,
0,
};
TTMaskZero(mask);
while ((c = *s++))
while (c = *s++)
{
switch (c)
{
@ -439,7 +418,7 @@ CmdParseLayers(
type = DBTechNameTypes(name, &newmask);
if (type == -2)
{
which = LookupStruct(name, (const LookupTable *) special, sizeof special[0]);
which = LookupStruct(name, (LookupTable *) special, sizeof special[0]);
if (which >= 0)
{
switch (special[which].layer_value)
@ -461,7 +440,7 @@ CmdParseLayers(
|| (window->w_client != DBWclientID))
return (FALSE);
crec = (DBWclientRec *) window->w_clientData;
DBSeeTypesAll(((CellUse *)window->w_surfaceID),
DBSeeTypesAll(((CellUse *)window->w_surfaceID),
&rootRect, crec->dbw_bitmask, &newmask);
TTMaskAndMask(&newmask, &crec->dbw_visibleLayers);
tempmask = DBAllButSpaceAndDRCBits;
@ -530,7 +509,7 @@ printTypes:
return (TRUE);
}
/*
* ----------------------------------------------------------------------------
*
@ -549,8 +528,8 @@ printTypes:
*/
TileType
cmdMaskToType(
TileTypeBitMask *mask)
cmdMaskToType(mask)
TileTypeBitMask *mask;
{
TileType type, t;
@ -569,7 +548,7 @@ cmdMaskToType(
return (TT_SPACE);
return (type);
}
/*
* ----------------------------------------------------------------------------
*
@ -595,21 +574,19 @@ cmdMaskToType(
*/
void
cmdSaveCell(
CellDef *cellDef, /* Pointer to def of cell to be saved */
char *newName, /* Pointer to name of file in which cell is to be
cmdSaveCell(cellDef, newName, noninteractive, tryRename)
CellDef *cellDef; /* Pointer to def of cell to be saved */
char *newName; /* Pointer to name of file in which cell is to be
* saved. May be NULL, in which case the name from
* the CellDef is taken.
*/
bool noninteractive,/* If true, try hard but don't ask the user
bool noninteractive;/* If true, try hard but don't ask the user
* questions.
*/
bool tryRename) /* We should rename the cell to the name of the
bool tryRename; /* We should rename the cell to the name of the
* place where it was saved.
*/
{
char *fileName = newName;
/* Eliminate the phony labels added for use by rsim */
#ifndef NO_SIM_MODULE
SimEraseLabels();
@ -620,46 +597,46 @@ cmdSaveCell(
* cell changes to the name of the file in which it was
* saved.
*/
if (strcmp(cellDef->cd_name, UNNAMED) == 0)
{
if (newName == NULL)
TxPrintf("Must specify name for cell %s.\n", UNNAMED);
fileName = cmdCheckNewName(cellDef, newName, TRUE, noninteractive);
if (fileName == NULL) return;
newName = cmdCheckNewName(cellDef, newName, TRUE, noninteractive);
if (newName == NULL) return;
}
else if (newName != NULL)
{
fileName = cmdCheckNewName(cellDef, newName, TRUE, noninteractive);
if (fileName == NULL) return;
newName = cmdCheckNewName(cellDef, newName, TRUE, noninteractive);
if (newName == NULL) return;
}
else
{
if (cellDef->cd_file == NULL)
{
fileName = cmdCheckNewName(cellDef, cellDef->cd_name,
newName = cmdCheckNewName(cellDef, cellDef->cd_name,
TRUE, noninteractive);
if (fileName == NULL) return;
if (newName == NULL) return;
}
}
DBUpdateStamps(cellDef);
if (!DBCellWrite(cellDef, fileName))
DBUpdateStamps();
if (!DBCellWrite(cellDef, newName))
{
TxError("Could not write file. Cell not written.\n");
goto cleanup;
return;
}
if (!tryRename || (fileName == NULL) || (strcmp(cellDef->cd_name, fileName) == 0))
goto cleanup;
if (!tryRename || (newName == NULL) || (strcmp(cellDef->cd_name, newName) == 0))
return;
/* Rename the cell */
if (!DBCellRenameDef(cellDef, fileName))
if (!DBCellRenameDef(cellDef, newName))
{
/* This should never happen */
TxError("Magic error: there is already a cell named \"%s\"\n",
fileName);
goto cleanup;
newName);
return;
}
if (EditCellUse && (cellDef == EditCellUse->cu_def))
@ -678,16 +655,11 @@ cmdSaveCell(
* We want to find all windows for which this is
* the root cell and update their captions.
*/
(void) WindSearch(DBWclientID, (ClientData) NULL, (Rect *) NULL,
(void) WindSearch(DBWclientID, (ClientData) NULL, (Rect *) NULL,
cmdSaveWindSet, (ClientData) cellDef);
}
cleanup:
if ((fileName != newName) && (fileName != cellDef->cd_name))
freeMagic(fileName);
return;
}
/*
* ----------------------------------------------------------------------------
*
@ -714,51 +686,44 @@ cleanup:
*/
char *
cmdCheckNewName(
CellDef *def,
char *newName,
bool tryRename,
bool noninteractive)
cmdCheckNewName(def, newName, tryRename, noninteractive)
CellDef *def;
char *newName;
bool tryRename;
bool noninteractive;
{
static const char * const yesno[] = { "no", "yes", 0 };
static char newname[256];
static char *yesno[] = { "no", "yes", 0 };
char *filename;
char *prompt;
char *returnname;
int code;
FILE *f;
returnname = newName;
again:
if (returnname == NULL)
if (newName == NULL)
{
if (noninteractive) {
TxError("Can't write file named '%s'\n", def->cd_name);
return NULL;
};
TxPrintf("File for cell %s: [hit return to abort save] ", def->cd_name);
returnname = (char *)mallocMagic(1024 * sizeof(char));
if (TxGetLine(returnname, sizeof returnname) == NULL || returnname[0] == '\0')
if (TxGetLine(newname, sizeof newname) == NULL || newname[0] == '\0')
{
TxPrintf("Cell not saved.\n");
freeMagic(returnname);
return ((char *) NULL);
}
if (CmdIllegalChars(returnname, "[],", "Cell name"))
{
freeMagic(returnname);
if (CmdIllegalChars(newname, "[],", "Cell name"))
goto again;
}
newName = newname;
}
/* Remove any ".mag" file extension from the name */
if (strlen(returnname) > 4)
if (!strcmp(returnname + strlen(returnname) - 4, ".mag"))
*(returnname + strlen(returnname) - 4) = '\0';
else if (!strcmp(newName + strlen(newName) - 4, ".mag"))
*(newName + strlen(newName) - 4) = '\0';
if (strcmp(returnname, def->cd_name) != 0)
if (strcmp(newName, def->cd_name) != 0)
{
if ((f = PaOpen(returnname, "r", DBSuffix, ".", (char *) NULL, &filename)))
if (f = PaOpen(newName, "r", DBSuffix, ".", (char *) NULL, &filename))
{
(void) fclose(f);
if (noninteractive) {
@ -773,57 +738,25 @@ again:
if (code == 0)
{
/* No -- don't overwrite */
if (returnname != newName) freeMagic(returnname);
returnname = NULL;
newName = NULL;
goto again;
}
}
}
if (tryRename && DBCellLookDef(returnname) != NULL)
if (tryRename && DBCellLookDef(newName) != NULL)
{
TxError("Can't rename cell '%s' to '%s' because that cell already exists.\n",
def->cd_name, returnname);
if (returnname != newName) freeMagic(returnname);
def->cd_name, newName);
if (noninteractive) return NULL;
returnname = NULL;
newName = NULL;
goto again;
}
}
return (returnname);
return (newName);
}
/*
* ----------------------------------------------------------------------------
*
* nameEllipsis ---
*
* Truncate a string an append an ellipsis ("...") to the end if the string
* will overflow a fixed array length.
*
* ----------------------------------------------------------------------------
*/
static char *
nameEllipsis(
char *name,
int maxlen,
char **prefix)
{
int l = strlen(name);
if (l < maxlen)
{
*prefix = "";
return name;
}
else
{
*prefix = "...";
return &name[l - maxlen + 3];
}
}
/*
* ----------------------------------------------------------------------------
*
@ -848,25 +781,23 @@ nameEllipsis(
*/
int
cmdSaveWindSet(
MagWindow *window,
CellDef *def)
cmdSaveWindSet(window, def)
MagWindow *window;
CellDef *def;
{
char caption[200];
CellDef *rootDef;
char *name, *name_pfx;
rootDef = ((CellUse *) window->w_surfaceID)->cu_def;
if (rootDef != def)
return 0;
name = nameEllipsis(def->cd_name, 175, &name_pfx);
(void) snprintf(caption, sizeof(caption), "%s%s [NOT BEING EDITED]", name_pfx, name);
(void) sprintf(caption, "%s [NOT BEING EDITED]", def->cd_name);
(void) StrDup(&window->w_iconname, def->cd_name);
WindCaption(window, caption);
return 0;
}
/*
* ----------------------------------------------------------------------------
*
@ -902,20 +833,20 @@ static CellDef *newRootDef; /* Pointer to root def of window in which
*/
void
CmdSetWindCaption(
CellUse *newEditUse, /* Pointer to new edit cell use */
CellDef *rootDef) /* Root cell def of the window in which the
CmdSetWindCaption(newEditUse, rootDef)
CellUse *newEditUse; /* Pointer to new edit cell use */
CellDef *rootDef; /* Root cell def of the window in which the
* edit cell was selected.
*/
{
int cmdWindSet(MagWindow *window);
int cmdWindSet();
newEditDef = (newEditUse) ? newEditUse->cu_def : NULL;
newRootDef = rootDef;
(void) WindSearch(DBWclientID, (ClientData) NULL, (Rect *) NULL,
(void) WindSearch(DBWclientID, (ClientData) NULL, (Rect *) NULL,
cmdWindSet, (ClientData) 0);
}
/*
* ----------------------------------------------------------------------------
*
@ -943,27 +874,18 @@ CmdSetWindCaption(
*/
int
cmdWindSet(
MagWindow *window)
cmdWindSet(window)
MagWindow *window;
{
char caption[200];
CellDef *wDef;
char *name[2], *name_pfx[2];
wDef = ((CellUse *) window->w_surfaceID)->cu_def;
if (wDef != newRootDef) {
name[0] = nameEllipsis(wDef->cd_name, 175, &name_pfx[0]);
(void) snprintf(caption, sizeof(caption), "%s%s [NOT BEING EDITED]",
name_pfx[0], name[0]);
} else {
name[0] = nameEllipsis(wDef->cd_name, 90, &name_pfx[0]);
name[1] = nameEllipsis(newEditDef->cd_name, 90, &name_pfx[1]);
(void) snprintf(caption, sizeof(caption), "%s%s EDITING %s%s",
name_pfx[0], name[0], name_pfx[1], name[1]);
if (wDef != newRootDef)
(void) sprintf(caption, "%s [NOT BEING EDITED]", wDef->cd_name);
else {
(void) sprintf(caption, "%s EDITING %s", wDef->cd_name,
newEditDef->cd_name);
#ifdef SCHEME_INTERPRETER
/* Add a binding to scheme variable "edit-cell" */
LispSetEdit (newEditDef->cd_name);
@ -975,7 +897,7 @@ cmdWindSet(
return 0;
}
/*
* ----------------------------------------------------------------------------
*
@ -1000,9 +922,9 @@ cmdWindSet(
*/
MagWindow *
CmdGetRootPoint(
Point *point,
Rect *rect)
CmdGetRootPoint(point, rect)
Point *point;
Rect *rect;
{
MagWindow *window;
@ -1012,7 +934,7 @@ CmdGetRootPoint(
return (window);
}
/*
* ----------------------------------------------------------------------------
*
@ -1035,9 +957,9 @@ CmdGetRootPoint(
*/
MagWindow *
CmdGetEditPoint(
Point *point,
Rect *rect)
CmdGetEditPoint(point, rect)
Point *point;
Rect *rect;
{
MagWindow *window;
Rect rootRect;
@ -1052,7 +974,7 @@ CmdGetEditPoint(
return (window);
}
/*
* ----------------------------------------------------------------------------
*
@ -1072,11 +994,11 @@ CmdGetEditPoint(
*/
bool
CmdWarnWrite(void)
CmdWarnWrite()
{
int count, code;
int cmdWarnWriteFunc(CellDef *cellDef, int *pcount);
static const char * const yesno[] = { "no", "yes", 0 };
int cmdWarnWriteFunc();
static char *yesno[] = { "no", "yes", 0 };
char *prompt;
count = 0;
@ -1088,26 +1010,26 @@ CmdWarnWrite(void)
prompt = TxPrintString("%d Magic cell%s been modified.\n Do you"
" want to exit magic and lose %s? ", count,
count == 1 ? " has" : "s have",
count == 1 ? "it" : "them");
count == 1 ? "it" : "them");
code = TxDialog(prompt, yesno, 0);
return (code) ? TRUE : FALSE;
}
int
cmdWarnWriteFunc(
CellDef *cellDef,
int *pcount)
cmdWarnWriteFunc(cellDef, pcount)
CellDef *cellDef;
int *pcount;
{
if ((cellDef->cd_flags & CDINTERNAL) == 0)
(*pcount)++;
return 0;
}
/*
* ----------------------------------------------------------------------------
* cmdExpandOneLevel --
*
* Expand (unexpand) a cell, and unexpand all of its children. This is
* Expand (unexpand) a cell, and unexpand all of its children. This is
* called by commands such as getcell, expand current cell, and load.
* Don't bother to unexpand children if we are unexpanding this cell.
*
@ -1120,30 +1042,30 @@ cmdWarnWriteFunc(
*/
void
cmdExpandOneLevel(
CellUse *cu,
int bitmask,
bool expand)
cmdExpandOneLevel(cu, bitmask, expand)
CellUse *cu;
int bitmask;
bool expand;
{
extern int cmdExpand1func(CellUse *cu, ClientData bitmask);
extern int cmdExpand1func();
/* first, expand this cell use */
DBExpand(cu, bitmask, expand);
/* now, unexpand its direct children (ONE LEVEL ONLY) */
if (expand)
(void) DBCellEnum(cu->cu_def, cmdExpand1func, INT2CD(bitmask));
(void) DBCellEnum(cu->cu_def, cmdExpand1func, (ClientData) bitmask);
}
int
cmdExpand1func(
CellUse *cu,
ClientData bitmask)
cmdExpand1func(cu, bitmask)
CellUse *cu;
ClientData bitmask;
{
DBExpand(cu, (int)CD2INT(bitmask), FALSE);
DBExpand(cu, (int) bitmask, FALSE);
return 0;
}
/*
* ----------------------------------------------------------------------------
*
@ -1168,13 +1090,13 @@ Transform *cmdSelTrans; /* Shared between CmdGetSelectedCell and
*/
CellUse *
CmdGetSelectedCell(
Transform *pTrans) /* If non-NULL, transform from selected
CmdGetSelectedCell(pTrans)
Transform *pTrans; /* If non-NULL, transform from selected
* cell to root coords is stored here.
*/
{
CellUse *result = NULL;
int cmdGetSelFunc(CellUse *selUse, CellUse *realUse, Transform *transform, CellUse **pResult); /* Forward declaration. */
int cmdGetSelFunc(); /* Forward declaration. */
cmdSelTrans = pTrans;
(void) SelEnumCells(FALSE, (bool *) NULL, (SearchContext *) NULL,
@ -1184,29 +1106,18 @@ CmdGetSelectedCell(
/* ARGSUSED */
int
cmdGetSelFunc(
CellUse *selUse, /* Not used. */
CellUse *realUse, /* The first selected use. */
Transform *transform, /* Transform from coords of realUse to root. */
CellUse **pResult) /* Store realUse here. */
cmdGetSelFunc(selUse, realUse, transform, pResult)
CellUse *selUse; /* Not used. */
CellUse *realUse; /* The first selected use. */
Transform *transform; /* Transform from coords of realUse to root. */
CellUse **pResult; /* Store realUse here. */
{
*pResult = realUse;
if (cmdSelTrans != NULL)
*cmdSelTrans = *transform;
return 1; /* Skip any other selected cells. */
}
/* The Open Group, Sep 2006, Austin/317 deprecated isascii(),
* Apparently it cannot be used portably in a localized application.
*/
static int
magic_isascii(int c)
{
return (c & ~0x7f) == 0;
}
/*
* ----------------------------------------------------------------------------
*
@ -1227,10 +1138,10 @@ magic_isascii(int c)
*/
bool
CmdIllegalChars(
char *string, /* String to check for illegal chars. */
char *illegal, /* String containing illegal chars. */
char *msg) /* String identifying what string is
CmdIllegalChars(string, illegal, msg)
char *string; /* String to check for illegal chars. */
char *illegal; /* String containing illegal chars. */
char *msg; /* String identifying what string is
* supposed to represent, for ease in
* printing error messages.
*/
@ -1239,7 +1150,7 @@ CmdIllegalChars(
for (p = string; *p != 0; p++)
{
if (!magic_isascii(*p)) goto error;
if (!isascii(*p)) goto error;
if (iscntrl(*p)) goto error;
for (bad = illegal; *bad != 0; bad++)
{
@ -1248,7 +1159,7 @@ CmdIllegalChars(
continue;
error:
if (!magic_isascii(*p) || iscntrl(*p))
if (!isascii(*p) || iscntrl(*p))
{
TxError("%s contains illegal control character 0x%x\n",
msg, *p);

File diff suppressed because it is too large Load Diff

View File

@ -6,25 +6,24 @@
* These commands are not intended to be used by the ordinary magic
* user, but are provided for the benefit of system maintainers/implementors.
*
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
*/
#ifndef lint
static const char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magic-8.0/commands/CmdWizard.c,v 1.2 2008/02/10 19:30:19 tim Exp $";
static char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magic-8.0/commands/CmdWizard.c,v 1.2 2008/02/10 19:30:19 tim Exp $";
#endif /* not lint */
#include <stdio.h>
#include <stdint.h>
#include <stdlib.h>
#include <string.h>
#include <sys/types.h>
@ -47,20 +46,13 @@ static const char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magi
#include "utils/utils.h"
#include "textio/txcommands.h"
/* For diagnostics */
#include "cif/CIFint.h"
#include "database/databaseInt.h"
/* C99 compat */
#include "extract/extract.h"
/* Forward declarations */
extern void cmdPsearchStats(char *str, struct tms *tl, struct tms *td, int count);
extern void cmdPsearchStats();
void cmdStatsHier(CellDef *, int, CellDef *);
/*
* ----------------------------------------------------------------------------
*
@ -83,9 +75,9 @@ void cmdStatsHier(CellDef *, int, CellDef *);
*/
void
CmdCoord(
MagWindow *w,
TxCommand *cmd)
CmdCoord(w, cmd)
MagWindow *w;
TxCommand *cmd;
{
MagWindow *pointW = (MagWindow *) NULL;
Rect editRect, rootRect;
@ -163,7 +155,7 @@ CmdCoord(
editRect.r_xtop, editRect.r_ytop);
TxPrintf("\n");
}
/*
* ----------------------------------------------------------------------------
*
@ -185,242 +177,15 @@ CmdCoord(
#ifndef NO_EXT
void
CmdExtractTest(
MagWindow *w,
TxCommand *cmd)
CmdExtractTest(w, cmd)
MagWindow *w;
TxCommand *cmd;
{
ExtractTest(w, cmd);
}
#endif
/*
* ----------------------------------------------------------------------------
*
* tileCountProc --
*
* Routine to count tiles.
*
* Return:
* 0 to keep the search going
*
* Side effects:
* Keeps count in clientData
*
* ----------------------------------------------------------------------------
*/
int
tileCountProc(
Tile *tile,
int *tcount)
{
(*tcount)++;
return 0;
}
/*
* ----------------------------------------------------------------------------
*
* showMem --
* CmdShowmem --
*
* Usage:
*
* showmem [outfile]
*
* Display all the (principle) internal memory usage for tiles, including
* all cell defs, and all CIF generated planes.
*
* Results:
* None.
*
* Side effects:
* May write to a disk file.
*
* ----------------------------------------------------------------------------
*/
void
showMem(
FILE *outf, /* File to which information is to be output */
bool verbose) /* If TRUE, output detailed erase table */
{
int ttotal, ttotal1, ttotal2;
int i;
Plane *plane;
CellDef *def;
int pNum;
HashSearch hs;
HashEntry *entry;
fprintf(outf, "Tile memory usage summary\n");
fprintf(outf, "Technology %s\n", DBTechName);
/* Search every cell def (including internal ones), count tiles,
* and add up the tile memory usage on every plane.
*/
/* Search the CIFPlanes and count tiles. */
/* CIFPlanes, CIFTotalPlanes, CIFComponentPlanes */
ttotal2 = 0;
if (CIFCurStyle != NULL)
{
fprintf(outf, "\nCIFPlanes:\n");
ttotal1 = 0;
for (i = 0; i < MAXCIFLAYERS; i++)
{
plane = CIFPlanes[i];
if (plane != NULL)
{
ttotal = 0;
DBSrPaintArea((Tile *)NULL, plane, &TiPlaneRect,
&DBAllTypeBits, tileCountProc, &ttotal);
ttotal1 += ttotal;
if (CIFCurStyle->cs_layers[i])
fprintf(outf, " layer %s: %ld\n",
CIFCurStyle->cs_layers[i]->cl_name,
(long)ttotal * (long)sizeof(Tile));
else
fprintf(outf, " layer %d: %d\n", i,
(long)ttotal * (long)sizeof(Tile));
}
}
fprintf(outf, " Subtotal: %ld bytes\n",
(long)ttotal1 * (long)sizeof(Tile));
ttotal2 += ttotal1;
fprintf(outf, "\nCIFTotalPlanes\n");
ttotal1 = 0;
for (i = 0; i < MAXCIFLAYERS; i++)
{
plane = CIFTotalPlanes[i];
if (plane != NULL)
{
ttotal = 0;
DBSrPaintArea((Tile *)NULL, plane, &TiPlaneRect,
&DBAllTypeBits, tileCountProc, &ttotal);
ttotal1 += ttotal;
if (CIFCurStyle->cs_layers[i])
fprintf(outf, " layer %s: %ld\n",
CIFCurStyle->cs_layers[i]->cl_name,
(long)ttotal * (long)sizeof(Tile));
else
fprintf(outf, " layer %d: %d\n", i,
(long)ttotal * (long)sizeof(Tile));
}
}
fprintf(outf, " Subtotal: %ld bytes\n",
(long)ttotal1 * (long)sizeof(Tile));
ttotal2 += ttotal1;
fprintf(outf, "\nCIFComponentPlanes\n");
ttotal1 = 0;
for (i = 0; i < MAXCIFLAYERS; i++)
{
plane = CIFComponentPlanes[i];
if (plane != NULL)
{
ttotal = 0;
DBSrPaintArea((Tile *)NULL, plane, &TiPlaneRect,
&DBAllTypeBits, tileCountProc, &ttotal);
ttotal1 += ttotal;
if (CIFCurStyle->cs_layers[i])
fprintf(outf, " layer %s: %ld bytes\n",
CIFCurStyle->cs_layers[i]->cl_name,
(long)ttotal * (long)sizeof(Tile));
else
fprintf(outf, " layer %d: %ld bytes\n", i,
(long)ttotal * (long)sizeof(Tile));
}
}
fprintf(outf, " Subtotal: %ld bytes\n",
(long)ttotal1 * (long)sizeof(Tile));
ttotal2 += ttotal1;
}
else
{
fprintf(outf, "CIF planes: No memory usage\n");
}
HashStartSearch(&hs);
while ((entry = HashNext(&dbCellDefTable, &hs)) != NULL)
{
def = (CellDef *)HashGetValue(entry);
if (def != (CellDef *)NULL)
{
fprintf(outf, "\nCell def %s\n", def->cd_name);
ttotal1 = 0;
for (pNum = 0; pNum < DBNumPlanes; pNum++)
{
plane = def->cd_planes[pNum];
if (plane != NULL)
{
ttotal = 0;
DBSrPaintArea((Tile *)NULL, plane, &TiPlaneRect,
&DBAllTypeBits, tileCountProc, &ttotal);
fprintf(outf, " plane %s: %ld bytes\n",
DBPlaneLongNameTbl[pNum],
(long)ttotal * (long)sizeof(Tile));
ttotal1 += ttotal;
}
}
fprintf(outf, " Subtotal: %ld bytes\n",
(long)ttotal1 * (long)sizeof(Tile));
ttotal2 += ttotal1;
}
}
fprintf(outf, " Grand total: %ld bytes\n",
(long)ttotal2 * (long)sizeof(Tile));
}
void
CmdShowmem(
MagWindow *w,
TxCommand *cmd)
{
FILE *outf;
bool verbose;
char **av;
int ac;
if (cmd->tx_argc > 3)
{
TxError("Usage: showmem [-v] [file]\n");
return;
}
verbose = FALSE;
av = &cmd->tx_argv[1];
ac = cmd->tx_argc - 1;
outf = stdout;
if (ac > 0 && strcmp(av[0], "-v") == 0)
{
verbose = TRUE;
av++, ac--;
}
if (ac > 0)
{
outf = fopen(av[0], "w");
if (outf == (FILE *) NULL)
{
perror(av[0]);
TxError("Nothing written\n");
return;
}
}
showMem(outf, verbose);
if (outf != stdout)
(void) fclose(outf);
}
/*
* ----------------------------------------------------------------------------
*
@ -443,9 +208,9 @@ CmdShowmem(
*/
void
showTech(
FILE *outf, /* File to which information is to be output */
bool verbose) /* If TRUE, output detailed erase table */
showTech(outf, verbose)
FILE *outf; /* File to which information is to be output */
bool verbose; /* If TRUE, output detailed erase table */
{
int i, j;
int pNum;
@ -463,7 +228,7 @@ showTech(
fprintf(outf, "\n");
fprintf(outf, "Types:\n");
for (i = 0; i < DBNumTypes; i++) {
int pl ; const char *spl ;
int pl ; char *spl ;
pl = DBPlane(i);
spl = ( pl <= 0 || pl > DBNumPlanes ) ? "??" : DBPlaneLongName(pl);
@ -590,9 +355,9 @@ showTech(
}
void
CmdShowtech(
MagWindow *w,
TxCommand *cmd)
CmdShowtech(w, cmd)
MagWindow *w;
TxCommand *cmd;
{
FILE *outf;
bool verbose;
@ -632,7 +397,7 @@ CmdShowtech(
(void) fclose(outf);
}
/*
* ----------------------------------------------------------------------------
*
@ -658,16 +423,16 @@ CmdShowtech(
*/
void
CmdTilestats(
MagWindow *w,
TxCommand *cmd)
CmdTilestats(w, cmd)
MagWindow *w;
TxCommand *cmd;
{
CellUse *selectedUse;
FILE *outf = stdout;
bool allDefs = FALSE;
char **av = cmd->tx_argv + 1;
int ac = cmd->tx_argc - 1;
int cmdStatsFunc(CellDef *def, FILE *outf);
int cmdStatsFunc();
if (ac > 2)
{
@ -742,12 +507,11 @@ int totalTiles[TT_MAXTYPES];
*/
int
cmdStatsFunc(
CellDef *def,
FILE *outf)
cmdStatsFunc(def, outf)
CellDef *def;
FILE *outf;
{
int cmdStatsCount(CellDef *def, struct countClient *cc);
int cmdStatsOutput(CellDef *def, struct countClient *cc);
int cmdStatsCount(), cmdStatsOutput();
struct countClient cc;
int total;
TileType t;
@ -796,11 +560,11 @@ cmdStatsFunc(
*/
int
cmdStatsCount(
CellDef *def,
struct countClient *cc)
cmdStatsCount(def, cc)
CellDef *def;
struct countClient *cc;
{
int cmdStatsCountTile(Tile *tile, struct cellInfo *ci);
int cmdStatsCountTile();
int pNum;
struct cellInfo *ci;
TileType t;
@ -827,9 +591,9 @@ cmdStatsCount(
}
int
cmdStatsCountTile(
Tile *tile,
struct cellInfo *ci)
cmdStatsCountTile(tile, ci)
Tile *tile;
struct cellInfo *ci;
{
TileType type = TiGetType(tile);
@ -870,10 +634,9 @@ cmdStatsCountTile(
*/
void
cmdStatsHier(
CellDef *parent,
int nuses,
CellDef *child)
cmdStatsHier(parent, nuses, child)
CellDef *parent, *child;
int nuses;
{
struct cellInfo *pi, *ci;
TileType t;
@ -918,9 +681,9 @@ cmdStatsHier(
*/
int
cmdStatsOutput(
CellDef *def,
struct countClient *cc)
cmdStatsOutput(def, cc)
CellDef *def;
struct countClient *cc;
{
TileType t;
struct cellInfo *ci;
@ -958,7 +721,7 @@ cmdStatsOutput(
freeMagic((char *) ci);
return (0);
}
/*
* ----------------------------------------------------------------------------
*
@ -983,11 +746,11 @@ cmdStatsOutput(
*/
void
CmdPsearch(
MagWindow *w,
TxCommand *cmd)
CmdPsearch(w, cmd)
MagWindow *w;
TxCommand *cmd;
{
char *RunStats(int flags, struct tms *lastt, struct tms *deltat);
char *RunStats();
static struct tms tlast, tdelta;
Point p;
Plane *plane;
@ -1049,13 +812,12 @@ CmdPsearch(
}
void
cmdPsearchStats(
char *str,
struct tms *tl,
struct tms *td,
int count)
cmdPsearchStats(str, tl, td, count)
char *str;
struct tms *tl, *td;
int count;
{
char *RunStats(int flags, struct tms *lastt, struct tms *deltat);
char *RunStats();
char *rstatp;
int us, ups;
@ -1064,13 +826,13 @@ cmdPsearchStats(
ups = us / count;
TxPrintf("%s: %d searches, %d us/search [%s]\n", str, count, ups, rstatp);
}
/*
* ----------------------------------------------------------------------------
*
* CmdTsearch --
*
* Call DBSrPaintArea() a number of times over an area the size and shape of
* Call TiSrArea() a number of times over an area the size and shape of
* that specified by the box, each time over a different area in the
* edit cell.
*
@ -1095,13 +857,12 @@ int numTilesFound;
bool cmdTsearchDebug = FALSE;
void
CmdTsearch(
MagWindow *w,
TxCommand *cmd)
CmdTsearch(w, cmd)
MagWindow *w;
TxCommand *cmd;
{
int cmdTsrFunc(Tile *tp);
char *RunStats(int flags, struct tms *lastt, struct tms *deltat);
char *rstatp;
int cmdTsrFunc();
char *RunStats(), *rstatp;
static TileTypeBitMask mask;
static struct tms tlast, tdelta;
Rect rtool, rsearch;
@ -1153,7 +914,7 @@ CmdTsearch(
if (!TTMaskEqual(&mask, &DBZeroTypeBits))
numTilesFound = 0;
for (i = 0; i < count; i++)
{
/*****
@ -1182,12 +943,18 @@ CmdTsearch(
if (cmd->tx_argc < 5)
{
(void) DBSrPaintArea((Tile *) NULL, plane, &rsearch, &DBAllTypeBits,
(void) TiSrArea((Tile *) NULL, plane, &rsearch,
cmdTsrFunc, (ClientData) 0);
}
else
{
(void) DBSrPaintArea((Tile *) NULL, plane, &rsearch, &mask,
/****
if (strcmp(cmd->tx_argv[4], "mayo") == 0)
(void) TiSrAreaNR2((Tile *) NULL, plane, &rsearch, &mask,
cmdTsrFunc, (ClientData) 0);
else
****/
(void) DBSrPaintArea((Tile *) NULL, plane, &rsearch, &mask,
cmdTsrFunc, (ClientData) 0);
}
}
@ -1208,15 +975,15 @@ CmdTsearch(
}
int
cmdTsrFunc(
Tile *tp)
cmdTsrFunc(tp)
Tile *tp;
{
if (cmdTsearchDebug)
TxPrintf("%lx\n", (intptr_t) tp);
TxPrintf("%x\n", tp);
numTilesFound++;
return 0;
}
/*
* ----------------------------------------------------------------------------
*
@ -1235,9 +1002,9 @@ cmdTsrFunc(
*/
void
CmdWatch(
MagWindow *w,
TxCommand *cmd)
CmdWatch(w, cmd)
MagWindow *w;
TxCommand *cmd;
{
DBWclientRec *crec;
int pNum;
@ -1278,7 +1045,7 @@ CmdWatch(
pNum = DBTechNamePlane(cmd->tx_argv[1]);
if (pNum < 0)
{
const char *cp;
char *cp;
TxError("Unrecognized plane: %s. Legal names are:\n",
cmd->tx_argv[1]);
for(pNum=0; pNum < PL_MAXTYPES; pNum++) {
@ -1288,16 +1055,8 @@ CmdWatch(
};
return;
}
if (EditCellUse != NULL)
{
crec->dbw_watchDef = EditCellUse->cu_def;
crec->dbw_watchTrans = EditToRootTransform;
}
else
{
crec->dbw_watchDef = ((CellUse *)w->w_surfaceID)->cu_def;
crec->dbw_watchTrans = ((CellUse *)w->w_surfaceID)->cu_transform;
}
crec->dbw_watchDef = EditCellUse->cu_def;
crec->dbw_watchTrans = EditToRootTransform;
}
crec->dbw_watchPlane = pNum;

62
commands/Depend Normal file
View File

@ -0,0 +1,62 @@
CmdSubrs.o: CmdSubrs.c ../utils/magic.h ../utils/geometry.h \
../utils/utils.h ../database/database.h ../tiles/tile.h ../utils/hash.h \
../windows/windows.h ../dbwind/dbwind.h ../utils/main.h \
../commands/commands.h ../textio/textio.h ../cif/cif.h ../drc/drc.h \
../textio/txcommands.h ../utils/undo.h ../utils/macros.h ../sim/sim.h \
../select/select.h
CmdAB.o: CmdAB.c ../tcltk/tclmagic.h ../utils/magic.h ../utils/geometry.h \
../tiles/tile.h ../utils/hash.h ../database/database.h \
../windows/windows.h ../dbwind/dbwind.h ../utils/main.h \
../commands/commands.h ../utils/utils.h ../textio/textio.h ../drc/drc.h \
../cif/cif.h ../graphics/graphics.h ../textio/txcommands.h \
../utils/malloc.h ../utils/netlist.h ../select/select.h
CmdCD.o: CmdCD.c ../tcltk/tclmagic.h ../utils/magic.h ../utils/geometry.h \
../tiles/tile.h ../utils/hash.h ../database/database.h \
../windows/windows.h ../dbwind/dbwind.h ../utils/main.h \
../commands/commands.h ../utils/utils.h ../textio/textio.h ../drc/drc.h \
../graphics/graphics.h ../textio/txcommands.h ../cif/cif.h \
../calma/calma.h ../utils/styles.h ../router/rtrDcmpose.h \
../select/select.h ../utils/signals.h ../utils/malloc.h ../cif/CIFint.h \
../cif/CIFread.h
CmdE.o: CmdE.c ../tcltk/tclmagic.h ../utils/magic.h ../utils/styles.h \
../utils/geometry.h ../utils/utils.h ../tiles/tile.h ../utils/hash.h \
../database/database.h ../windows/windows.h ../graphics/graphics.h \
../dbwind/dbwind.h ../utils/main.h ../commands/commands.h \
../textio/textio.h ../utils/macros.h ../drc/drc.h ../textio/txcommands.h \
../extract/extract.h ../select/select.h
CmdFI.o: CmdFI.c ../tcltk/tclmagic.h ../utils/magic.h ../utils/geometry.h \
../utils/utils.h ../utils/undo.h ../tiles/tile.h ../utils/hash.h \
../database/database.h ../windows/windows.h ../dbwind/dbwind.h \
../utils/main.h ../commands/commands.h ../textio/textio.h \
../utils/macros.h ../drc/drc.h ../textio/txcommands.h ../utils/styles.h \
../graphics/graphics.h ../extract/extract.h ../utils/malloc.h \
../select/select.h ../sim/sim.h ../gcr/gcr.h
CmdLQ.o: CmdLQ.c ../tcltk/tclmagic.h ../utils/magic.h ../utils/malloc.h \
../utils/geometry.h ../utils/utils.h ../tiles/tile.h ../utils/hash.h \
../database/database.h ../database/fonts.h ../windows/windows.h \
../dbwind/dbwind.h ../utils/main.h ../commands/commands.h \
../textio/textio.h ../graphics/graphics.h ../drc/drc.h \
../textio/txcommands.h ../utils/undo.h ../select/select.h \
../netmenu/netmenu.h
CmdRS.o: CmdRS.c ../tcltk/tclmagic.h ../utils/magic.h ../utils/stack.h \
../utils/geometry.h ../utils/utils.h ../tiles/tile.h ../utils/hash.h \
../database/database.h ../database/fonts.h ../windows/windows.h \
../dbwind/dbwind.h ../utils/main.h ../commands/commands.h \
../textio/textio.h ../graphics/graphics.h ../utils/tech.h ../drc/drc.h \
../textio/txcommands.h ../utils/malloc.h ../utils/netlist.h \
../netmenu/netmenu.h ../select/select.h ../utils/signals.h ../sim/sim.h
CmdTZ.o: CmdTZ.c ../tcltk/tclmagic.h ../utils/magic.h ../utils/malloc.h \
../utils/geometry.h ../utils/utils.h ../tiles/tile.h ../utils/hash.h \
../database/database.h ../windows/windows.h ../dbwind/dbwind.h \
../utils/main.h ../commands/commands.h ../textio/textio.h \
../textio/txcommands.h ../utils/signals.h ../utils/undo.h \
../select/select.h ../utils/styles.h ../wiring/wiring.h \
../utils/netlist.h ../netmenu/netmenu.h ../utils/tech.h ../drc/drc.h
CmdWizard.o: CmdWizard.c ../utils/magic.h ../utils/geometry.h \
../utils/malloc.h ../tiles/tile.h ../utils/hash.h ../database/database.h \
../windows/windows.h ../dbwind/dbwind.h ../utils/main.h \
../commands/commands.h ../utils/runstats.h ../textio/textio.h \
../graphics/graphics.h ../utils/signals.h ../utils/utils.h \
../textio/txcommands.h
CmdAuto.o: CmdAuto.c ../tcltk/tclmagic.h ../utils/magic.h \
../utils/geometry.h ../windows/windows.h ../textio/txcommands.h

View File

@ -12,9 +12,10 @@ SRCS = CmdSubrs.c CmdAB.c CmdCD.c CmdE.c CmdFI.c \
module: ${MAGICDIR}/readline/readline lib${MODULE}.o
# Delegate this task to the readline/Makefile
${MAGICDIR}/readline/readline:
${MAKE} -C ${MAGICDIR}/readline readline-create-symlinks
@if ( ! test -f ${MAGICDIR}/readline/readline ) ; then \
(cd ${MAGICDIR}/readline; ln -s `ls | grep readline` readline) ; \
fi
include ${MAGICDIR}/defs.mak
include ${MAGICDIR}/rules.mak

View File

@ -3,16 +3,16 @@
*
* Definitions for the commands module.
*
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
*
* Needs to include: tiles.h, database.h
@ -20,12 +20,11 @@
* rcsid $Header: /usr/cvsroot/magic-8.0/commands/commands.h,v 1.3 2009/01/19 15:43:03 tim Exp $
*/
#ifndef _MAGIC__COMMANDS__COMMANDS_H
#define _MAGIC__COMMANDS__COMMANDS_H
#ifndef _COMMANDS_H
#define _COMMANDS_H
#include "windows/windows.h"
#include "database/database.h"
#include "textio/txcommands.h" /* TxCommand */
/*
* Name of default yank buffer
@ -51,28 +50,18 @@ extern TileTypeBitMask CmdYMAllButSpace;
/* --------------------- Global procedure headers --------------------- */
extern MagWindow *CmdGetEditPoint(Point *point, Rect *rect);
extern MagWindow *CmdGetRootPoint(Point *point, Rect *rect);
extern bool CmdWarnWrite(void);
extern bool CmdParseLayers(char *s, TileTypeBitMask *mask);
extern void CmdLabelProc(char *text, int font, int size, int rotate, int offx, int offy,
int pos, bool sticky, TileType type);
extern void CmdSetWindCaption(CellUse *newEditUse, CellDef *rootDef);
extern CellUse *CmdGetSelectedCell(Transform *pTrans);
extern bool CmdIllegalChars(char *string, char *illegal, char *msg);
extern TileType CmdFindNetProc(char *nodename, CellUse *use, Rect *rect, bool warn_not_found, bool *isvalid);
extern bool CmdCheckForPaintFunc(void);
extern MagWindow *CmdGetRootBox();
extern MagWindow *CmdGetEditPoint();
extern MagWindow *CmdGetRootPoint();
extern bool CmdWarnWrite();
extern bool CmdParseLayers();
extern void CmdAddSlop();
extern void CmdLabelProc();
extern void CmdSetWindCaption();
extern CellUse *CmdGetSelectedCell();
extern bool CmdIllegalChars();
extern void CmdDoMacro();
extern TileType CmdFindNetProc();
extern bool CmdCheckForPaintFunc();
/* C99 compat */
extern int cmdScaleCoord(MagWindow *w, char *arg, bool is_relative, bool is_x, int scale);
extern void FlatCopyAllLabels(SearchContext *scx, TileTypeBitMask *mask, int xMask, CellUse *targetUse);
extern bool cmdDumpParseArgs(char *cmdName, MagWindow *w, TxCommand *cmd, CellUse *dummy, SearchContext *scx);
extern void cmdFlushCell(CellDef *def, bool force_deref);
extern int cmdParseCoord(MagWindow *w, char *arg, bool is_relative, bool is_x);
extern void cmdSaveCell(CellDef *cellDef, char *newName, bool noninteractive, bool tryRename);
extern void CmdInit(void);
extern void CmdDoProperty(CellDef *def, TxCommand *cmd, int argstart);
extern void CmdPaintEraseButton(MagWindow *w, Point *refPoint, bool isPaint, bool isScreen);
#endif /* _MAGIC__COMMANDS__COMMANDS_H */
#endif /* _COMMANDS_H */

2
configure vendored
View File

@ -9,4 +9,4 @@
# script itself. It also sets up CFLAGS without the default optimizer
# flag (-O2).
( CFLAGS=${CFLAGS:-"-g"}; export CFLAGS; cd scripts ; ./configure "$@" )
( CFLAGS="-g"; export CFLAGS; cd scripts ; ./configure $* )

View File

@ -3,16 +3,16 @@
*
* Computation of boundaries of a database tile plane.
*
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
*/
@ -25,44 +25,31 @@ static char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magic-8.0/
#include "utils/geometry.h"
#include "database/database.h"
#include "tiles/tile.h"
typedef struct dbcellboundstruct
{
Rect *area;
Rect *extended;
bool extended;
bool found;
} DBCellBoundStruct;
/*
* --------------------------------------------------------------------
* DBBoundCellPlane ---
*
* Find the extents of all subcells of the cell "def", both the
* extent of geometry (rect) and the extent of geometry plus any
* labels extending outside the extent of geometry (extended).
*
* Results:
* TRUE if subcells were found and measured; FALSE if no subcells
* were found (in which case "extended" and "rect" may not be
* valid).
*
* Side effects:
* Values may be recorded in "extended" and "rect".
* --------------------------------------------------------------------
*/
int
DBBoundCellPlane(def, extended, rect)
CellDef *def;
Rect *extended;
bool extended;
Rect *rect;
{
TreeFilter filter;
DBCellBoundStruct cbs;
int dbCellBoundFunc();
Plane *plane;
filter.tf_func = NULL;
filter.tf_arg = (ClientData)&cbs;
@ -71,32 +58,48 @@ DBBoundCellPlane(def, extended, rect)
cbs.found = FALSE;
*rect = GeoNullRect;
if (DBSrCellPlaneArea(def->cd_cellPlane, &TiPlaneRect,
dbCellBoundFunc, (ClientData) &filter) == 0)
if (TiSrArea((Tile *)NULL, def->cd_planes[PL_CELL],
&TiPlaneRect, dbCellBoundFunc, (ClientData) &filter) == 0)
return cbs.found;
else
return -1;
}
int
dbCellBoundFunc(use, fp)
CellUse *use;
dbCellBoundFunc(tile, fp)
Tile *tile;
TreeFilter *fp;
{
CellUse *use;
CellTileBody *body;
Rect *bbox;
DBCellBoundStruct *cbs;
cbs = (DBCellBoundStruct *)fp->tf_arg;
if (cbs->found)
for (body = (CellTileBody *) TiGetBody(tile); body != NULL;
body = body->ctb_next)
{
GeoInclude(&use->cu_extended, cbs->extended);
GeoInclude(&use->cu_bbox, cbs->area);
}
else
{
*cbs->extended = use->cu_extended;
*cbs->area = use->cu_bbox;
cbs->found = TRUE;
use = body->ctb_use;
bbox = &use->cu_bbox;
if ((BOTTOM(tile) <= bbox->r_ybot) && (RIGHT(tile) >= bbox->r_xtop))
{
if (cbs->found)
{
if (cbs->extended)
GeoInclude(&use->cu_extended, cbs->area);
else
GeoInclude(&use->cu_bbox, cbs->area);
}
else
{
if (cbs->extended)
*cbs->area = use->cu_extended;
else
*cbs->area = use->cu_bbox;
cbs->found = TRUE;
}
}
}
return 0;
}
@ -178,7 +181,7 @@ DBBoundPlane(plane, rect)
return (TRUE);
}
/*
* --------------------------------------------------------------------
*

View File

@ -3,16 +3,16 @@
*
* Place and Delete subcells
*
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
*/
@ -37,7 +37,7 @@ int placeCellFunc();
int deleteCellFunc();
Tile * clipCellTile();
void dupTileBody();
void cellTileMerge();
void cellTileMerge();
bool ctbListMatch();
void freeCTBList();
@ -45,7 +45,7 @@ struct searchArg
{
CellUse * celluse;
Rect * rect;
BPlane * bplane;
Plane * plane;
};
#define TOPLEFT 10
@ -55,22 +55,7 @@ struct searchArg
#define TOPBOTTOMLEFTRIGHT 15
int dbCellDebug = 0;
void
dbInstanceUnplace(CellUse *use)
{
ASSERT(use != (CellUse *) NULL, "dbInstanceUnplace");
/* It's important that this code run with interrupts disabled,
* or else we could leave the subcell tile plane in a weird
* state.
*/
BPDelete(use->cu_parent->cd_cellPlane, use);
}
/*
* ----------------------------------------------------------------------------
*
@ -101,73 +86,33 @@ DBCellFindDup(use, parent)
* something identical to use?
*/
{
BPEnum bpe;
CellUse *dupUse;
Tile *tile;
CellTileBody *body;
CellUse *checkUse;
BPEnumInit(&bpe, parent->cd_cellPlane, &use->cu_bbox, BPE_EQUAL,
"DBCellFindDup");
while ((dupUse = BPEnumNext(&bpe)))
if (dupUse->cu_def == use->cu_def)
{
bool transMatch, arrayMatch, notXarray, notYarray;
/* Transforms must be equal---Aligned bounding boxes are
* an insufficient measure of exact overlap. Also, array
* counts and separation must match for arrayed devices
*/
transMatch = ((dupUse->cu_transform.t_a == use->cu_transform.t_a) &&
(dupUse->cu_transform.t_b == use->cu_transform.t_b) &&
(dupUse->cu_transform.t_c == use->cu_transform.t_c) &&
(dupUse->cu_transform.t_d == use->cu_transform.t_d) &&
(dupUse->cu_transform.t_e == use->cu_transform.t_e) &&
(dupUse->cu_transform.t_f == use->cu_transform.t_f));
/* First check if both use and dupUse are not arrays. */
notXarray = (dupUse->cu_xhi == dupUse->cu_xlo) &&
(use->cu_xhi == use->cu_xlo);
notYarray = (dupUse->cu_yhi == dupUse->cu_ylo) &&
(use->cu_yhi == use->cu_ylo);
arrayMatch = (notXarray && notYarray);
/* If they are arrays, then the array parameters must match. */
if (!notXarray && notYarray)
{
arrayMatch = ((dupUse->cu_xhi - dupUse->cu_xlo) ==
(use->cu_xhi - use->cu_xlo)) &&
(dupUse->cu_xsep == use->cu_xsep);
}
else if (!notYarray && notXarray)
{
arrayMatch = ((dupUse->cu_yhi - dupUse->cu_ylo) ==
(use->cu_yhi - use->cu_ylo)) &&
(dupUse->cu_ysep == use->cu_ysep);
}
else if (!notYarray && !notXarray)
{
arrayMatch = (((dupUse->cu_xhi - dupUse->cu_xlo) ==
(use->cu_xhi - use->cu_xlo)) &&
(dupUse->cu_xsep == use->cu_xsep)) &&
(((dupUse->cu_yhi - dupUse->cu_ylo) ==
(use->cu_yhi - use->cu_ylo)) &&
(dupUse->cu_ysep == use->cu_ysep));
}
if (transMatch && arrayMatch)
break;
}
BPEnumTerm(&bpe);
return dupUse;
tile = TiSrPoint((Tile *) NULL, parent->cd_planes[PL_CELL],
&use->cu_bbox.r_ll);
for (body = (CellTileBody *) TiGetBody(tile);
body != NULL;
body = body->ctb_next)
{
checkUse = body->ctb_use;
if (use->cu_def != checkUse->cu_def) continue;
if ((use->cu_bbox.r_xbot != checkUse->cu_bbox.r_xbot)
|| (use->cu_bbox.r_xtop != checkUse->cu_bbox.r_xtop)
|| (use->cu_bbox.r_ybot != checkUse->cu_bbox.r_ybot)
|| (use->cu_bbox.r_ytop != checkUse->cu_bbox.r_ytop))
continue;
return checkUse;
}
return (CellUse *) NULL;
}
/*
* ----------------------------------------------------------------------------
*
* DBPlaceCell --
* DBPlaceCellNoModify --
*
* Add a CellUse to the subcell tile plane of a CellDef.
* Assumes prior check that the new CellUse is not an exact duplicate
@ -185,74 +130,41 @@ DBCellFindDup(use, parent)
*/
void
DBPlaceCell (use, def)
CellUse * use; /* new celluse to add to subcell tile plane */
CellDef * def; /* parent cell's definition */
DBPlaceCell (celluse, targetcell)
CellUse * celluse; /* new celluse to add to subcell tile plane */
CellDef * targetcell; /* parent cell's definition */
{
Rect rect; /* argument to DBSrCellPlaneArea(), placeCellFunc() */
BPlane *bplane; /* argument to DBSrCellPlaneArea(), placeCellFunc() */
struct searchArg arg; /* argument to placeCellFunc() */
Rect rect; /* argument to TiSrArea(), placeCellFunc() */
Plane * plane; /* argument to TiSrArea(), placeCellFunc() */
struct searchArg arg; /* argument to placeCellFunc() */
ASSERT(use != (CellUse *) NULL, "DBPlaceCell");
ASSERT(def, "DBPlaceCell");
/* To do: Check non-duplicate placement, check non-duplicate ID */
use->cu_parent = def;
ASSERT(celluse != (CellUse *) NULL, "DBPlaceCell");
celluse->cu_parent = targetcell;
plane = targetcell->cd_planes[PL_CELL]; /* assign plane */
rect = celluse->cu_bbox;
/* rect = celluse->cu_extended; */
arg.rect = &rect;
arg.celluse = celluse;
arg.plane = plane;
/* Be careful not to permit interrupts during this, or the
* database could be left in a trashed state.
*/
SigDisableInterrupts();
BPAdd(def->cd_cellPlane, use);
def->cd_flags |= CDMODIFIED|CDGETNEWSTAMP;
(void) TiSrArea((Tile *) NULL, plane, &rect, placeCellFunc,
(ClientData) &arg);
targetcell->cd_flags |= CDMODIFIED|CDGETNEWSTAMP;
if (UndoIsEnabled())
DBUndoCellUse(use, UNDO_CELL_PLACE);
DBUndoCellUse(celluse, UNDO_CELL_PLACE);
SigEnableInterrupts();
}
/* Like DBPlaceCell(), but don't change the flags of the parent cell. */
/* This is needed by the bounding box recalculation routine, which may */
/* cause the cell to be deleted and replaced for the purpose of */
/* capturing the bounding box information in the BPlane structure, but */
/* this does not mean that anything in the parent cell has changed. */
void
DBPlaceCellNoModify (use, def)
CellUse * use; /* new celluse to add to subcell tile plane */
CellDef * def; /* parent cell's definition */
{
Rect rect; /* argument to DBSrCellPlaneArea(), placeCellFunc() */
BPlane *bplane; /* argument to DBSrCellPlaneArea(), placeCellFunc() */
struct searchArg arg; /* argument to placeCellFunc() */
ASSERT(use != (CellUse *) NULL, "DBPlaceCell");
ASSERT(def, "DBPlaceCell");
/* To do: Check non-duplicate placement, check non-duplicate ID */
use->cu_parent = def;
/* Be careful not to permit interrupts during this, or the
* database could be left in a trashed state.
*/
SigDisableInterrupts();
BPAdd(def->cd_cellPlane, use);
if (UndoIsEnabled())
DBUndoCellUse(use, UNDO_CELL_PLACE);
SigEnableInterrupts();
}
/*
* ----------------------------------------------------------------------------
* DBDeleteCell --
*
* Remove a CellUse from the subcell tile plane of a CellDef.
* If "nomodify" is TRUE, then don't set the parent cell's CDMODIFIED flag.
* This is needed when recomputing the bounding box, which should not by
* itself change the modified state.
*
* Results:
* None.
@ -264,10 +176,19 @@ DBPlaceCellNoModify (use, def)
*/
void
DBDeleteCell (use)
CellUse * use;
DBDeleteCell (celluse)
CellUse * celluse;
{
ASSERT(use != (CellUse *) NULL, "DBDeleteCell");
Rect rect; /* argument to TiSrArea(), deleteCellFunc() */
Plane * plane; /* argument to TiSrArea(), deleteCellFunc() */
struct searchArg arg; /* argument to deleteCellFunc() */
ASSERT(celluse != (CellUse *) NULL, "DBDeleteCell");
plane = celluse->cu_parent->cd_planes[PL_CELL]; /* assign plane */
rect = celluse->cu_bbox;
arg.rect = &rect;
arg.plane = plane;
arg.celluse = celluse;
/* It's important that this code run with interrupts disabled,
* or else we could leave the subcell tile plane in a weird
@ -275,47 +196,511 @@ DBDeleteCell (use)
*/
SigDisableInterrupts();
dbInstanceUnplace(use);
use->cu_parent->cd_flags |= CDMODIFIED|CDGETNEWSTAMP;
(void) TiSrArea((Tile *) NULL, plane, &rect, deleteCellFunc,
(ClientData) &arg);
celluse->cu_parent->cd_flags |= CDMODIFIED|CDGETNEWSTAMP;
if (UndoIsEnabled())
DBUndoCellUse(use, UNDO_CELL_DELETE);
use->cu_parent = (CellDef *) NULL;
DBUndoCellUse(celluse, UNDO_CELL_DELETE);
celluse->cu_parent = (CellDef *) NULL;
SigEnableInterrupts();
}
/*
* ----------------------------------------------------------------------------
* DBDeleteCellNoModify --
* placeCellFunc --
*
* Remove a CellUse from the subcell tile plane of a CellDef, as above,
* but don't set the parent cell's CDMODIFIED flag. This is needed when
* recomputing the bounding box, which should not by itself change the
* modified state.
* Add a new subcell to a tile.
* Clip the tile with respect to the subcell's bounding box.
* Insert the new CellTileBody into the linked list in ascending order
* based on the celluse pointer.
* This function is passed to TiSrArea.
*
* Results:
* 0 is always returned.
*
* Side effects:
* Modifies the subcell tile plane of the appropriate CellDef.
* Allocates a new CellTileBody.
* ----------------------------------------------------------------------------
*/
int
placeCellFunc (tile, arg)
Tile * tile; /* target tile */
struct searchArg * arg; /* celluse, rect, plane */
{
Tile * tp;
CellTileBody * body, * ctp, * ctplast;
#ifdef CELLDEBUG
if (dbCellDebug) TxPrintf("placeCellFunc called %x\n",tile);
#endif /* CELLDEBUG */
tp = clipCellTile (tile, arg->plane, arg->rect);
body = (CellTileBody *) mallocMagic((unsigned) (sizeof (CellTileBody)));
body->ctb_use = arg->celluse;
ctp = (CellTileBody *) tp->ti_body;
ctplast = ctp;
while ((ctp != (CellTileBody *) NULL) && (ctp->ctb_use > body->ctb_use))
{
ctplast = ctp;
ctp = ctp->ctb_next;
}
body->ctb_next = ctp;
if (ctp == (CellTileBody *) tp->ti_body) /* empty list or front of list */
TiSetBody(tp, body);
else /* after at least one CellTileBody */
ctplast->ctb_next = body;
/* merge tiles back into the the plane */
/* requires that TiSrArea visit tiles in NW to SE wavefront */
if ( RIGHT(tp) == arg->rect->r_xtop)
{
if (BOTTOM(tp) == arg->rect->r_ybot)
cellTileMerge (tp, arg->plane, TOPBOTTOMLEFTRIGHT);
else
cellTileMerge (tp, arg->plane, TOPLEFTRIGHT);
}
else if (BOTTOM(tp) == arg->rect->r_ybot)
cellTileMerge (tp, arg->plane, TOPBOTTOMLEFT);
else
cellTileMerge (tp, arg->plane, TOPLEFT);
return 0;
}
/*
* ----------------------------------------------------------------------------
* deleteCellFunc --
*
* Remove a subcell from a tile.
* This function is passed to TiSrArea.
*
* Results:
* Always returns 0.
*
* Side effects:
* Modifies the subcell tile plane of the appropriate CellDef.
* Deallocates a CellTileBody.
* ----------------------------------------------------------------------------
*/
int
deleteCellFunc (tile, arg)
Tile * tile;
struct searchArg * arg; /* plane, rect */
{
CellTileBody * ctp; /* CellTileBody to be freed */
CellTileBody * ctplast; /* follows one behind ctp */
CellUse * celluse;
#ifdef CELLDEBUG
if (dbCellDebug) TxPrintf("deleteCellFunc called %x\n",tile);
#endif /* CELLDEBUG */
celluse = arg->celluse;
/* find the appropriate CellTileBody in the linked list */
ctp = (CellTileBody *) tile->ti_body;
ctplast = ctp;
while ((ctp != (CellTileBody *) NULL) && (ctp->ctb_use != celluse))
{
ctplast = ctp;
ctp = ctp->ctb_next;
}
/* there should have been a match */
if (ctp == (CellTileBody *) NULL)
{
ASSERT (ctp != (CellTileBody *) NULL, "deleteCellFunc");
return 0;
}
/* relink the list with one CellTileBody deleted */
if (ctp == ctplast) /* front of list */
TiSetBody(tile, ctp->ctb_next);
else /* beyond front of list */
ctplast->ctb_next = ctp->ctb_next;
freeMagic((char *) ctp);
/* merge tiles back into the the plane */
/* requires that TiSrArea visit tiles in NW to SE wavefront */
if ( RIGHT(tile) == arg->rect->r_xtop)
{
if (BOTTOM(tile) == arg->rect->r_ybot)
cellTileMerge (tile, arg->plane, TOPBOTTOMLEFTRIGHT);
else
cellTileMerge (tile, arg->plane, TOPLEFTRIGHT);
}
else if (BOTTOM(tile) == arg->rect->r_ybot)
cellTileMerge (tile, arg->plane, TOPBOTTOMLEFT);
else
cellTileMerge (tile, arg->plane, TOPLEFT);
return (0);
}
/*
* ----------------------------------------------------------------------------
* clipCellTile --
*
* Clip the given tile against the given rectangle.
*
* Results:
* Returns a pointer to the clipped tile.
*
* Side effects:
* Modifies the database plane that contains the given tile.
* ----------------------------------------------------------------------------
*/
Tile *
clipCellTile (tile, plane, rect)
Tile * tile;
Plane * plane;
Rect * rect;
{
Tile * newtile;
if (TOP(tile) > rect->r_ytop)
{
#ifdef CELLDEBUG
if (dbCellDebug) TxPrintf("clipCellTile calls TiSplitY TOP\n");
#endif /* CELLDEBUG */
newtile = TiSplitY (tile, rect->r_ytop); /* no merge */
dupTileBody (tile, newtile);
}
if (BOTTOM(tile) < rect->r_ybot)
{
#ifdef CELLDEBUG
if (dbCellDebug) TxPrintf("clipCellTile calls TiSplitY BOTTOM\n");
#endif /* CELLDEBUG */
newtile = tile;
tile = TiSplitY (tile, rect->r_ybot); /* no merge */
dupTileBody (newtile, tile);
}
if (RIGHT(tile) > rect->r_xtop)
{
#ifdef CELLDEBUG
if (dbCellDebug) TxPrintf("clipCellTile calls TiSplitX RIGHT\n");
#endif /* CELLDEBUG */
newtile = TiSplitX (tile, rect->r_xtop);
dupTileBody (tile, newtile);
cellTileMerge (newtile, plane, TOPBOTTOM);
}
if (LEFT(tile) < rect->r_xbot)
{
#ifdef CELLDEBUG
if (dbCellDebug) TxPrintf("clipCellTile calls TiSplitX LEFT\n");
#endif /* CELLDEBUG */
newtile = tile;
tile = TiSplitX (tile, rect->r_xbot);
dupTileBody (newtile, tile);
cellTileMerge (newtile, plane, TOPBOTTOM);
}
return (tile);
} /* clipCellTile */
/*
* ----------------------------------------------------------------------------
* dupTileBody --
*
* Duplicate the body of an old tile as the body for a new tile.
*
* Results:
* None.
*
* Side effects:
* Allocates new CellTileBodies unless the old tile was a space tile.
* ----------------------------------------------------------------------------
*/
void
dupTileBody (oldtp, newtp)
Tile * oldtp;
Tile * newtp;
{
CellTileBody * oldctb, * newctb, * newctblast;
oldctb = (CellTileBody *) oldtp->ti_body;
if (oldctb != (CellTileBody *) NULL)
{
newctb = (CellTileBody *) mallocMagic((unsigned) (sizeof (CellTileBody)));
TiSetBody(newtp, newctb);
newctb->ctb_use = oldctb->ctb_use;
oldctb = oldctb->ctb_next;
newctblast = newctb;
while (oldctb != (CellTileBody *) NULL)
{
newctb = (CellTileBody *) mallocMagic((unsigned) (sizeof (CellTileBody)));
newctblast->ctb_next = newctb;
newctb->ctb_use = oldctb->ctb_use;
oldctb = oldctb->ctb_next;
newctblast = newctb;
}
newctblast->ctb_next = (CellTileBody *) NULL;
}
else TiSetBody(newtp, NULL);
} /* dupTileBody */
/*
* ----------------------------------------------------------------------------
* cellTileMerge --
*
* Merge the given tile with its plane in the directions specified.
*
* Results:
* None.
*
* Side effects:
* Modifies the subcell tile plane of the CellDef, sets the
* parent pointer of the deleted CellUse to NULL.
* Modifies the database plane that contains the given tile.
* ----------------------------------------------------------------------------
*/
void
DBDeleteCellNoModify (use)
CellUse * use;
cellTileMerge (tile, plane, direction)
Tile * tile;
Plane * plane;
int direction; /* TOP = 8, BOTTOM = 4, LEFT = 2, RIGHT = 1 */
{
ASSERT(use != (CellUse *) NULL, "DBDeleteCell");
Point topleft, bottomright;
Tile * dummy, * tpleft, * tpright, * tp1, * tp2;
/* It's important that this code run with interrupts disabled,
* or else we could leave the subcell tile plane in a weird
* state.
*/
#ifdef CELLDEBUG
if (dbCellDebug) TxPrintf("cellTileMerge %x\n",tile);
#endif /* CELLDEBUG */
SigDisableInterrupts();
dbInstanceUnplace(use);
if (UndoIsEnabled())
DBUndoCellUse(use, UNDO_CELL_DELETE);
use->cu_parent = (CellDef *) NULL;
SigEnableInterrupts();
topleft.p_x = LEFT(tile);
topleft.p_y = TOP(tile);
bottomright.p_x = RIGHT(tile);
bottomright.p_y = BOTTOM(tile);
if ((direction >> 1) % 2) /* LEFT */
{
tpright = tile;
tpleft = BL(tpright);
#ifdef CELLDEBUG
if (dbCellDebug) TxPrintf("LEFT %x %x\n",tpleft,tpright);
#endif /* CELLDEBUG */
while (BOTTOM(tpleft) < topleft.p_y) /* go up left edge */
{
if (ctbListMatch (tpleft, tpright))
{
if (BOTTOM(tpleft) < BOTTOM(tpright))
{
dummy = tpleft;
tpleft = TiSplitY (tpleft, BOTTOM (tpright));
dupTileBody (dummy, tpleft);
}
else if (BOTTOM(tpleft) > BOTTOM(tpright))
{
dummy = tpright;
tpright = TiSplitY (tpright, BOTTOM (tpleft));
dupTileBody (dummy, tpright);
}
if (TOP(tpleft) > TOP(tpright))
{
dummy = TiSplitY (tpleft, TOP(tpright));
dupTileBody (tpleft, dummy);
}
else if (TOP(tpright) > TOP(tpleft))
{
dummy = TiSplitY (tpright, TOP(tpleft));
dupTileBody (tpright, dummy);
}
freeCTBList (tpright);
TiJoinX (tpleft, tpright, plane); /* tpright disappears */
tpright = RT(tpleft);
if (BOTTOM(tpright) < topleft.p_y) tpleft = BL(tpright);
else tpleft = tpright; /* we're off the top of the tile */
/* this will break the while loop */
} /* if (ctbListMatch (tpleft, tpright)) */
else tpleft = RT(tpleft);
} /* while */
tile = tpleft; /* for TiSrPoint in next IF statement */
}
if (direction % 2) /* RIGHT */
{
tpright = TiSrPoint (tile, plane, &bottomright);
--(bottomright.p_x);
tpleft = TiSrPoint (tpright, plane, &bottomright);
++(bottomright.p_x);
#ifdef CELLDEBUG
if (dbCellDebug) TxPrintf("RIGHT %x %x\n",tpleft,tpright);
#endif /* CELLDEBUG */
while (BOTTOM(tpright) < topleft.p_y) /* go up right edge */
{
if (ctbListMatch (tpleft, tpright))
{
if (BOTTOM(tpright) < BOTTOM(tpleft))
{
dummy = tpright;
tpright = TiSplitY (tpright, BOTTOM(tpleft));
dupTileBody (dummy, tpright);
}
else if (BOTTOM(tpleft) < BOTTOM(tpright))
{
dummy = tpleft;
tpleft = TiSplitY (tpleft, BOTTOM(tpright));
dupTileBody (dummy, tpleft);
}
if (TOP(tpright) > TOP(tpleft))
{
dummy = TiSplitY (tpright, TOP(tpleft));
dupTileBody (tpright, dummy);
}
else if (TOP(tpleft) > TOP(tpright))
{
dummy = TiSplitY (tpleft, TOP(tpright));
dupTileBody (tpleft, dummy);
}
freeCTBList (tpright);
TiJoinX (tpleft, tpright, plane); /* tpright disappears */
tpright = RT(tpleft);
while (LEFT(tpright) > bottomright.p_x) tpright = BL(tpright);
/* tpleft can be garbage if we're off the top of the loop, */
/* but it doesn't matter since the expression tests tpright */
tpleft = BL(tpright);
} /* if (ctbListMatch (tpleft, tpright)) */
else
{
tpright = RT(tpright);
while (LEFT(tpright) > bottomright.p_x) tpright = BL(tpright);
tpleft = BL(tpright); /* left side merges may have */
/* created more tiles */
}
} /* while */
tile = tpright; /* for TiSrPoint in next IF statement */
}
if ((direction >> 3) % 2) /* TOP */
{
tp1 = TiSrPoint (tile, plane, &topleft); /* merge across top */
--(topleft.p_y);
tp2 = TiSrPoint (tile, plane, &topleft);/* top slice of original tile */
++(topleft.p_y);
#ifdef CELLDEBUG
if (dbCellDebug) TxPrintf("TOP %x %x\n",tp1,tp2);
#endif /* CELLDEBUG */
if ((LEFT(tp1) == LEFT(tp2) ) &&
(RIGHT(tp1) == RIGHT(tp2)) &&
(ctbListMatch (tp1, tp2) ))
{
freeCTBList (tp2);
TiJoinY (tp1, tp2, plane);
}
tile = tp1; /* for TiSrPoint in next IF statement */
}
if ((direction >> 2) % 2) /* BOTTOM */
{
--(bottomright.p_x);
/* bottom slice of orig tile */
tp1 = TiSrPoint (tile, plane, &bottomright);
--(bottomright.p_y);
tp2 = TiSrPoint (tile, plane, &bottomright); /* merge across bottom */
#ifdef CELLDEBUG
if (dbCellDebug) TxPrintf("BOTTOM %x %x\n",tp1,tp2);
#endif /* CELLDEBUG */
if ((LEFT(tp1) == LEFT(tp2) ) &&
(RIGHT(tp1) == RIGHT(tp2)) &&
(ctbListMatch (tp1, tp2) ))
{
freeCTBList (tp2);
TiJoinY (tp1, tp2, plane);
}
}
}
/*
* ----------------------------------------------------------------------------
* freeCTBList --
*
* Free all CellTileBodies attached to the give tile.
*
* Results:
* None.
*
* Side effects:
* Frees CellTileBodies.
* ----------------------------------------------------------------------------
*/
void
freeCTBList (tile)
Tile * tile;
{
CellTileBody * ctp, * ctplast;
ctp = (CellTileBody *) tile->ti_body;
while (ctp != (CellTileBody *) NULL)
{
ctplast = ctp;
ctp = ctp->ctb_next;
freeMagic((char *) ctplast);
}
TiSetBody(tile, NULL);
}
/*
* ----------------------------------------------------------------------------
* ctbListMatch --
*
* Compare two linked lists of CellTileBodies, assuming that they are
* sorted in ascending order by celluse pointers.
*
* Results:
* True if the tiles have identical lists of CellTileBodies.
*
* Side effects:
* None.
* ----------------------------------------------------------------------------
*/
bool
ctbListMatch (tp1, tp2)
Tile * tp1, * tp2;
{
CellTileBody * ctp1, * ctp2;
ctp1 = (CellTileBody *) tp1->ti_body;
ctp2 = (CellTileBody *) tp2->ti_body;
while (ctp1 && ctp2 && (ctp1->ctb_use == ctp2->ctb_use))
ctp1 = ctp1->ctb_next, ctp2 = ctp2->ctb_next;
return ((ctp1 == (CellTileBody *) NULL) && (ctp2 == (CellTileBody *) NULL));
}

View File

@ -4,16 +4,16 @@
* Procedures for calculating and changing cell bounding boxes,
* and for manipulating arrays of cells.
*
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
*/
@ -34,7 +34,7 @@ static char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magic-8.0/
#include "dbwind/dbwind.h"
#include "utils/undo.h"
/*
*-----------------------------------------------------------------------------
*
@ -59,15 +59,15 @@ static char rcsid[] __attribute__ ((unused)) = "$Header: /usr/cvsroot/magic-8.0/
*/
char *
DBPrintUseId(
SearchContext *scx, /* Pointer to current search context, specifying a
DBPrintUseId(scx, name, size, display_only)
SearchContext *scx; /* Pointer to current search context, specifying a
* cell use and X,Y array indices.
*/
char *name, /* Pointer to string into which we will copy the
char *name; /* Pointer to string into which we will copy the
* print name of this instance.
*/
int size, /* Maximum number of characters to copy into string. */
bool display_only) /* TRUE if called for displaying only */
int size; /* Maximum number of characters to copy into string. */
bool display_only; /* TRUE if called for displaying only */
{
CellUse *use = scx->scx_use;
char *sp, *id, *ep;
@ -105,7 +105,7 @@ DBPrintUseId(
return (sp);
}
/*
* ----------------------------------------------------------------------------
*
@ -143,7 +143,7 @@ DBCellClearAvail(cellDef)
{
cellDef->cd_flags &= ~(CDNOTFOUND|CDAVAILABLE);
}
/*
* ----------------------------------------------------------------------------
*
@ -185,7 +185,7 @@ DBCellSetModified(cellDef, ismod)
if (ismod)
cellDef->cd_flags |= CDMODIFIED|CDGETNEWSTAMP;
}
/*
* ----------------------------------------------------------------------------
*
@ -253,7 +253,7 @@ DBComputeUseBbox(use)
GeoTransRect(&use->cu_transform, &childRect, &use->cu_bbox);
GeoTransRect(&use->cu_transform, &childExtend, &use->cu_extended);
}
/*
* ----------------------------------------------------------------------------
*
@ -276,7 +276,7 @@ DBIsChild(cu1, cu2)
{
return (cu1->cu_parent == cu2->cu_def);
}
/*
* ----------------------------------------------------------------------------
*
@ -305,7 +305,7 @@ DBSetArray(fromCellUse, toCellUse)
toCellUse->cu_xsep = fromCellUse->cu_xsep;
toCellUse->cu_ysep = fromCellUse->cu_ysep;
}
/*
* ----------------------------------------------------------------------------
*
@ -330,7 +330,7 @@ DBSetTrans(cellUse, trans)
cellUse->cu_transform = *trans;
DBComputeUseBbox(cellUse);
}
/*
* ----------------------------------------------------------------------------
*
@ -389,7 +389,7 @@ DBMakeArray(cellUse, rootToCell, xlo, ylo, xhi, yhi, xsep, ysep)
DBComputeUseBbox(cellUse);
}
/*
* ----------------------------------------------------------------------------
*
@ -483,7 +483,7 @@ DBArrayOverlap(cu, parentRect, pxlo, pxhi, pylo, pyhi)
* The intent is that "outlo" will be the smaller of the two
* coordinates, and "outhi" the larger.
*/
/* Even though it should never happen, handle zero spacings
* gracefully.
*/
@ -545,7 +545,7 @@ DBArrayOverlap(cu, parentRect, pxlo, pxhi, pylo, pyhi)
*pyhi = outyhi;
}
}
/*
* ----------------------------------------------------------------------------
*
@ -616,12 +616,16 @@ dbReComputeBboxFunc(cellDef, boundProc, recurseProc)
bool foundAny;
int pNum;
/* Cells which declare their bounding box to be fixed */
/* must return immediately. */
if (cellDef->cd_flags & CDFIXEDBBOX) return;
/*
* Include area of subcells separately
*/
if (!((foundAny = DBBoundCellPlane(cellDef, &extended, &rect)) > 0))
extended = GeoNullRect;
area = rect;
if ((foundAny = DBBoundCellPlane(cellDef, TRUE, &rect)) > 0)
area = rect;
for (pNum = PL_PAINTBASE; pNum < DBNumPlanes; pNum++)
if (pNum != PL_DRC_CHECK)
@ -635,7 +639,7 @@ dbReComputeBboxFunc(cellDef, boundProc, recurseProc)
}
/*
* Include the area of label anchors, too.
* Include the area of labels, too.
*/
for (label = cellDef->cd_labels; label != NULL; label = label->lab_next)
{
@ -657,11 +661,7 @@ dbReComputeBboxFunc(cellDef, boundProc, recurseProc)
}
}
/* Make sure the extended bounding box includes the area of all
* paint material just found, then include the area of all text
* in the current cell.
*/
GeoInclude(&area, &extended);
extended = area;
if (foundAny)
{
for (label = cellDef->cd_labels; label != NULL; label = label->lab_next)
@ -678,7 +678,6 @@ dbReComputeBboxFunc(cellDef, boundProc, recurseProc)
degenerate = TRUE;
area.r_xbot = area.r_ybot = 0;
area.r_xtop = area.r_ytop = 1;
extended = area;
}
else degenerate = FALSE;
@ -693,11 +692,7 @@ dbReComputeBboxFunc(cellDef, boundProc, recurseProc)
if (area.r_ybot == area.r_ytop)
area.r_ytop = area.r_ybot + 1;
if (extended.r_xbot == extended.r_xtop)
extended.r_xtop = extended.r_xbot + 1;
if (extended.r_ybot == extended.r_ytop)
extended.r_ytop = extended.r_ybot + 1;
if (degenerate) extended = area;
/* Did the bounding box change? If not then there's no need to
* recompute the parents. If the cell has no material, then
@ -733,7 +728,7 @@ dbReComputeBboxFunc(cellDef, boundProc, recurseProc)
*/
parent = use->cu_parent;
DBDeleteCellNoModify(use);
DBDeleteCell(use);
use->cu_parent = parent;
}
@ -761,7 +756,7 @@ dbReComputeBboxFunc(cellDef, boundProc, recurseProc)
if ((parent = use->cu_parent) != (CellDef *) NULL)
{
parent->cd_flags |= CDBOXESCHANGED;
DBPlaceCellNoModify(use, parent);
DBPlaceCell(use, parent);
if (last != parent)
{
if (last != NULL) (*recurseProc)(last);
@ -775,7 +770,7 @@ dbReComputeBboxFunc(cellDef, boundProc, recurseProc)
if ((last != NULL) && (parent != NULL)) (*recurseProc)(parent);
UndoEnable();
}
/*
* ----------------------------------------------------------------------------
*
@ -822,7 +817,7 @@ DBComputeArrayArea(area, cellUse, x, y, prect)
prect->r_ybot = area->r_ybot + ydelta;
prect->r_ytop = area->r_ytop + ydelta;
}
/*
* ----------------------------------------------------------------------------
*

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

View File

@ -3,16 +3,16 @@
*
* Cell selection.
*
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
* * Copyright (C) 1985, 1990 Regents of the University of California. *
* * Permission to use, copy, modify, and distribute this *
* * software and its documentation for any purpose and without *
* * fee is hereby granted, provided that the above copyright *
* * notice appear in all copies. The University of California *
* * makes no representations about the suitability of this *
* * software for any purpose. It is provided "as is" without *
* * express or implied warranty. Export of this software outside *
* * of the United States of America may require an export license. *
* *********************************************************************
*/
@ -55,7 +55,7 @@ struct selectArg
/* Forward declarations */
int dbSelectCellSr();
/*
* ----------------------------------------------------------------------------
*
@ -251,7 +251,7 @@ dbSelectCellSr(scx, arg)
/* compute lastArea (using long long to avoid overflow). */
{
int xDiff, yDiff;
xDiff = pbx->r_xtop - pbx->r_xbot;
yDiff = pbx->r_ytop - pbx->r_ybot;
/* BY NP */
@ -281,7 +281,7 @@ dbSelectCellSr(scx, arg)
n = arg->csa_bestpath->tp_last - arg->csa_bestpath->tp_next;
strncpy(arg->csa_bestpath->tp_next, cpath->tp_first, n);
arg->csa_bestpath->tp_next[n] = '\0';
/* Pop last component of current path */
cpath->tp_next = savenext;
*savenext = '\0';
@ -308,7 +308,7 @@ dbSelectCellSr(scx, arg)
/* compute bestArea (using long long to avoid overflow). */
{
int xDiff, yDiff;
xDiff = pbx->r_xtop - pbx->r_xbot;
yDiff = pbx->r_ytop - pbx->r_ybot;
bestArea = (dlong)xDiff * (dlong)yDiff;

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