Skip to content
Projects
Groups
Snippets
Help
This project
Loading...
Sign in / Register
Toggle navigation
S
sv2v
Overview
Overview
Details
Activity
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Board
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
lvzhengyang
sv2v
Commits
6eda946f
Commit
6eda946f
authored
Jun 15, 2024
by
Zachary Snow
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
handle directives when writing to a directory
parent
fdfa5971
Show whitespace changes
Inline
Side-by-side
Showing
6 changed files
with
194 additions
and
25 deletions
+194
-25
CHANGELOG.md
+10
-0
src/Job.hs
+1
-5
src/Split.hs
+106
-0
src/sv2v.hs
+10
-13
sv2v.cabal
+1
-0
test/write/run.sh
+66
-7
No files found.
CHANGELOG.md
View file @
6eda946f
## Unreleased
### Bug Fixes
*
Fixed
`--write path/to/dir/`
with directives like
`` `default_nettype ``
### Other Enhancements
*
`--write path/to/dir/`
can now also be used with
`--pass-through`
## v0.0.12
### Breaking Changes
...
...
src/Job.hs
View file @
6eda946f
...
...
@@ -139,11 +139,7 @@ readJob =
setWrite
::
Job
->
IO
Job
setWrite
job
=
do
w
<-
parseWrite
$
writeRaw
job
case
(
w
,
passThrough
job
)
of
(
Directory
{},
True
)
->
do
hPutStr
stderr
"can't use --pass-through when writing to a dir"
exitFailure
_
->
return
$
job
{
write
=
w
}
return
$
job
{
write
=
w
}
setSuccinct
::
Job
->
Job
setSuccinct
job
|
verbose
job
=
job
{
exclude
=
Succinct
:
exclude
job
}
...
...
src/Split.hs
0 → 100644
View file @
6eda946f
{- sv2v
- Author: Zachary Snow <zach@zachjs.com>
-
- Split descriptions into individual files
-}
module
Split
(
splitDescriptions
)
where
import
Data.List
(
isPrefixOf
)
import
Language.SystemVerilog.AST
splitDescriptions
::
AST
->
[
PackageItem
]
->
([(
String
,
AST
)],
[
PackageItem
])
splitDescriptions
(
PackageItem
item
:
ungrouped
)
itemsBefore
=
(
grouped
,
item
:
itemsAfter
)
where
(
grouped
,
itemsAfter
)
=
splitDescriptions
ungrouped
(
item
:
itemsBefore
)
splitDescriptions
(
description
:
descriptions
)
itemsBefore
=
((
name
,
surrounded
)
:
grouped
,
itemsAfter
)
where
(
grouped
,
itemsAfter
)
=
splitDescriptions
descriptions
itemsBefore
name
=
case
description
of
Part
_
_
_
_
x
_
_
->
x
Package
_
x
_
->
x
Class
_
x
_
_
->
x
surrounded
=
surroundDescription
itemsBefore
description
itemsAfter
splitDescriptions
[]
_
=
(
[]
,
[]
)
data
SurroundState
=
SurroundState
{
sKeptBefore
::
[
PackageItem
]
,
sKeptAfter
::
[
PackageItem
]
,
sCellDefine
::
Bool
,
sUnconnectedDrive
::
Maybe
PackageItem
,
sDefaultNettype
::
Maybe
PackageItem
,
sComment
::
Maybe
PackageItem
}
-- filter and include the surrounding package items for this description
surroundDescription
::
[
PackageItem
]
->
Description
->
[
PackageItem
]
->
AST
surroundDescription
itemsBefore
description
itemsAfter
=
map
PackageItem
itemsBefore'
++
description
:
map
PackageItem
itemsAfter'
where
itemsBefore'
=
extraBefore
++
reverse
(
sKeptBefore
state2
)
itemsAfter'
=
sKeptAfter
state2
++
reverse
extraAfter
state0
=
SurroundState
[]
[]
False
Nothing
Nothing
Nothing
state1
=
foldr
stepBefore
state0
itemsBefore
state2
=
foldr
stepAfter
state1
itemsAfter
(
extraBefore
,
extraAfter
)
=
foldr
(
<>
)
mempty
$
map
(
$
state2
)
$
[
applyLeader
sDefaultNettype
,
applyCellDefine
,
applyUnconnectedDrive
,
applyLeader
sComment
]
applyCellDefine
::
SurroundState
->
([
PackageItem
],
[
PackageItem
])
applyCellDefine
state
|
sCellDefine
state
=
([
Directive
"`celldefine"
],
[
Directive
"`endcelldefine"
])
|
otherwise
=
(
[]
,
[]
)
applyUnconnectedDrive
::
SurroundState
->
([
PackageItem
],
[
PackageItem
])
applyUnconnectedDrive
state
|
Just
item
<-
sUnconnectedDrive
state
=
([
item
],
[
Directive
"`nounconnected_drive"
])
|
otherwise
=
(
[]
,
[]
)
applyLeader
::
(
SurroundState
->
Maybe
PackageItem
)
->
SurroundState
->
([
PackageItem
],
[
PackageItem
])
applyLeader
getter
state
|
Just
item
<-
getter
state
=
([
item
],
[]
)
|
otherwise
=
(
[]
,
[]
)
-- update the state with a pre-description item
stepBefore
::
PackageItem
->
SurroundState
->
SurroundState
stepBefore
item
@
(
Decl
CommentDecl
{})
state
=
state
{
sComment
=
Just
item
}
stepBefore
item
@
(
Directive
directive
)
state
|
matches
"celldefine"
=
state
{
sCellDefine
=
True
}
|
matches
"endcelldefine"
=
state
{
sCellDefine
=
False
}
|
matches
"unconnected_drive"
=
state
{
sUnconnectedDrive
=
Just
item
}
|
matches
"nounconnected_drive"
=
state
{
sUnconnectedDrive
=
Nothing
}
|
matches
"default_nettype"
=
state
{
sDefaultNettype
=
Just
item
}
|
matches
"resetall"
=
state
{
sCellDefine
=
False
,
sUnconnectedDrive
=
Nothing
,
sDefaultNettype
=
Nothing
}
where
matches
=
flip
isPrefixOf
directive
.
(
'`'
:
)
stepBefore
item
state
=
state
{
sKeptBefore
=
item
:
sKeptBefore
state
}
-- update the state with a post-description item
stepAfter
::
PackageItem
->
SurroundState
->
SurroundState
stepAfter
(
Decl
CommentDecl
{})
state
=
state
stepAfter
(
Directive
directive
)
state
|
matches
"celldefine"
=
state
|
matches
"endcelldefine"
=
state
|
matches
"unconnected_drive"
=
state
|
matches
"nounconnected_drive"
=
state
|
matches
"default_nettype"
=
state
|
matches
"resetall"
=
state
where
matches
=
flip
isPrefixOf
directive
.
(
'`'
:
)
stepAfter
item
state
=
state
{
sKeptAfter
=
item
:
sKeptAfter
state
}
src/sv2v.hs
View file @
6eda946f
...
...
@@ -16,6 +16,7 @@ import Convert (convert)
import
Job
(
readJob
,
Job
(
..
),
Write
(
..
))
import
Language.SystemVerilog.AST
import
Language.SystemVerilog.Parser
(
parseFiles
,
Config
(
..
))
import
Split
(
splitDescriptions
)
isComment
::
Description
->
Bool
isComment
(
PackageItem
(
Decl
CommentDecl
{}))
=
True
...
...
@@ -60,17 +61,6 @@ rewritePath path = do
ext
=
".sv"
(
base
,
end
)
=
splitExtension
path
splitModules
::
FilePath
->
AST
->
[(
FilePath
,
String
)]
splitModules
dir
(
PackageItem
(
Decl
CommentDecl
{})
:
ast
)
=
splitModules
dir
ast
splitModules
dir
(
description
:
ast
)
=
(
path
,
output
)
:
splitModules
dir
ast
where
Part
_
_
Module
_
name
_
_
=
description
path
=
combine
dir
$
name
++
".v"
output
=
show
description
++
"
\n
"
splitModules
_
[]
=
[]
writeOutput
::
Write
->
[
FilePath
]
->
[
AST
]
->
IO
()
writeOutput
_
[]
[]
=
hPutStrLn
stderr
"Warning: No input files specified (try `sv2v --help`)"
...
...
@@ -82,9 +72,16 @@ writeOutput Adjacent inPaths asts = do
outPaths
<-
mapM
rewritePath
inPaths
let
results
=
map
(
++
"
\n
"
)
$
map
show
asts
zipWithM_
writeFile
outPaths
results
writeOutput
(
Directory
d
)
_
asts
=
do
let
(
outPaths
,
outputs
)
=
unzip
$
splitModules
d
$
concat
asts
writeOutput
(
Directory
d
)
_
asts
=
zipWithM_
writeFile
outPaths
outputs
where
(
outPaths
,
outputs
)
=
unzip
$
map
prepare
$
fst
$
splitDescriptions
(
concat
asts
)
[]
prepare
::
(
String
,
AST
)
->
(
FilePath
,
String
)
prepare
(
name
,
ast
)
=
(
path
,
output
)
where
path
=
combine
d
$
name
++
".v"
output
=
concatMap
(
++
"
\n
"
)
$
map
show
ast
main
::
IO
()
main
=
do
...
...
sv2v.cabal
View file @
6eda946f
...
...
@@ -116,6 +116,7 @@ executable sv2v
Convert.Wildcard
-- sv2v CLI modules
Job
Split
Paths_sv2v
autogen-modules:
Paths_sv2v
...
...
test/write/run.sh
View file @
6eda946f
...
...
@@ -89,13 +89,6 @@ test_directory() {
rm
-f
dirout/
*
mkdir
-p
dirout
runAndCapture
--pass-through
--write
dirout
*
.sv
assertFalse
"directory conversion should succeed"
$result
assertNull
"stdout should be empty"
"
$stdout
"
assertEquals
"stderr should have expected message"
\
"can't use --pass-through when writing to a dir"
\
"
$stderr
"
runAndCapture
--write
dirout
*
.sv
assertTrue
"directory conversion should succeed"
$result
assertNull
"stdout should be empty"
"
$stdout
"
...
...
@@ -104,12 +97,78 @@ test_directory() {
assertTrue
"one.v should exist"
"[ -f dirout/one.v ]"
assertTrue
"two.v should exist"
"[ -f dirout/two.v ]"
assertTrue
"three.v should exist"
"[ -f dirout/three.v ]"
assertFalse
"P.v should not exist"
"[ -f dirout/P.v ]"
actual
=
`
cat
dirout/
*
.v
`
assertEquals
"directory output should match combined"
"
$expected
"
"
$actual
"
clearArtifacts
}
test_directory_pass_through
()
{
rm
-f
dirout/
*
mkdir
-p
dirout
runAndCapture
--pass-through
--write
dirout
*
.sv
assertTrue
"directory conversion should succeed"
$result
assertNull
"stdout should be empty"
"
$stdout
"
assertNull
"stderr should be empty"
"
$stderr
"
assertTrue
"one.v should exist"
"[ -f dirout/one.v ]"
assertTrue
"two.v should exist"
"[ -f dirout/two.v ]"
assertTrue
"three.v should exist"
"[ -f dirout/three.v ]"
assertTrue
"P.v should exist"
"[ -f dirout/P.v ]"
clearArtifacts
}
test_directory_directives
()
{
module_inp
=
"logic a, b;module example;wire x;endmodule logic c, d;"
module_out
=
"logic a;
logic b;
module example;
wire x;
endmodule
logic c;
logic d;"
check_directory_example
"
$module_inp
"
"
$module_out
"
check_directory_example
"
\`
default_nettype none
\n
$module_inp
\`
resetall"
"
\`
default_nettype none
\n
$module_out
"
check_directory_example
"
\`
default_nettype none
\n\`
default_nettype wire
\n
$module_inp
"
"
\`
default_nettype wire
\n
$module_out
"
check_directory_example
"
\`
celldefine
\n
$module_inp
"
"
\`
celldefine
\n
$module_out
\n\`
endcelldefine"
check_directory_example
"
\`
celldefine
\n\`
endcelldefine
\n
$module_inp
"
"
$module_out
"
check_directory_example
"
\`
unconnected_drive pull0
\n
$module_inp
"
"
\`
unconnected_drive pull0
\n
$module_out
\n\`
nounconnected_drive"
check_directory_example
"
\`
unconnected_drive pull0
\n\`
nounconnected_drive
\n
$module_inp
"
"
$module_out
"
check_directory_example
"
\`
default_nettype none
\n\`
celldefine
\n\`
unconnected_drive pull1
\n\`
resetall
\n
$module_inp
"
"
$module_out
"
check_directory_example
"
\`
default_nettype none
\`
celldefine
\`
unconnected_drive pull1
$module_inp
"
"
\`
default_nettype none
\`
celldefine
\`
unconnected_drive pull1
$module_out
\`
nounconnected_drive
\`
endcelldefine"
}
check_directory_example
()
{
tmp_inp
=
$SHUNIT_TMPDIR
/example.sv
tmp_out
=
$SHUNIT_TMPDIR
/example.v
tmp_ref
=
$SHUNIT_TMPDIR
/example_ref.v
echo
-e
"
$1
"
>
$tmp_inp
echo
-e
"
$2
"
| sed
-E
's/ /\t/g'
>
$tmp_ref
rm
-f
$tmp_out
runAndCapture
--pass-through
--write
$SHUNIT_TMPDIR
$tmp_inp
assertTrue
"directory conversion should succeed"
$result
assertNull
"stdout should be empty:
$stdout
"
"
$stdout
"
assertNull
"stderr should be empty:
$stderr
"
"
$stderr
"
grep
-v
'//'
<
$tmp_out
>
$tmp_out
.bak
mv
$tmp_out
.bak
$tmp_out
output
=
`
diff
--unified
$tmp_ref
$tmp_out
`
assertTrue
"output doesn't match:
\n
$output
"
$?
}
test_unknown
()
{
runAndCapture
--write
=
unknown
*
.sv
assertFalse
"unknown write mode should fail"
$result
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment