Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[relay] Simulating lenet, add Relay to fud, other bug fixes. #504

Merged
merged 14 commits into from
May 13, 2021
Merged

Conversation

cgyurgyik
Copy link
Collaborator

@cgyurgyik cgyurgyik commented May 8, 2021

Lenet simulation

# TVM Softmax Calyx Softmax
0 7.1270239e-07 -0.00006103515625
1 1.1549375e-06 0.0002288818359375
2 3.7355226e-06 -0.0000457763671875
3 7.9318892e-07 0.0000457763671875
4 9.9998534e-01 1.0002899169921875
5 3.1714912e-08 -0.000030517578125
6 2.1043759e-06 -0.00006103515625
7 1.4363920e-06 -0.0004425048828125
8 3.1603065e-07 0.000030517578125
9 4.3458881e-06 0.0000457763671875

Given that our softmax output is producing negative numbers, there is still something wrong. I presume it is partly due to the fact that our current exp operator computes e^-x as 1/e^x. Tracking in #505.

Script to run ONNX models

More generally, I've written a script that takes in:

  1. The name of the net, e.g. lenet
  2. The file path to the input (i.e. the image).
  3. The dataset for which the input will be classified against. This is necessary to determine what preprocessing should be done on the image. e.g. "mnist", "imagenet".
  4. The file path to the ONNX model.
  5. Which output you want:
    (1) tvm, Running the Relay program on the TVM executor and printing the final softmax array.
    (2) calyx, Writing the Calyx program and data to files.
    (3) relay, Writing the Relay program to a file.

Example:

# Writes the Calyx program and data to separate files for simulation.
python3 frontends/relay/onnx_to_calyx.py -n "lenet" -d "MNIST" -i "/nets/four.png" -onnx "/nets/lenet.onnx" -o calyx

Other updates

  • Add a function to get a dictionary of memories from the Relay -> Calyx program.
  • Avoid overflow in nn.softmax by subtracting the max value first. As mentioned above, the exp operator still needs to be revamped.
  • Fix a bug in batch_flatten.
  • Add a subset of reshape (necessary for lenet), and dropout for future use.
  • Add relay to fud.
  • Add a round_float_to_fixed flag to the verilog stage that is currently defaulted to True. This flag essentially says any input from .data files will automatically be rounded to the nearest fixed point number.
  • Closes Testing the Relay frontend against a developed infrastructure. #494.

@cgyurgyik cgyurgyik added the C: Relay Relay-to-FuTIL compiler label May 8, 2021
@cgyurgyik cgyurgyik added this to the End of Spring 2021 milestone May 8, 2021
@cgyurgyik
Copy link
Collaborator Author

Blocked on Dahlia #372.

@cgyurgyik cgyurgyik added C: fud Calyx Driver S: Blocked Issue is blocked labels May 8, 2021
@cgyurgyik cgyurgyik removed the S: Blocked Issue is blocked label May 9, 2021
@rachitnigam
Copy link
Contributor

@cgyurgyik The Dahlia blocker has been fixed? Do you need to do anything else before we review?

@cgyurgyik
Copy link
Collaborator Author

@cgyurgyik The Dahlia blocker has been fixed? Do you need to do anything else before we review?

Nope. As usual, apologies for PR size. Most of it should be extra tests for cases that failed earlier. The slight variation to the expected softmax values is a result of using an implementation that avoids overflow.

@rachitnigam
Copy link
Contributor

Cool. Can I get help from some subset of @sgpthomas @EclecticGriffin and/or @sampsyo reviewing this?

@EclecticGriffin
Copy link
Collaborator

I can take a look later today (early evening)

Copy link
Collaborator

@EclecticGriffin EclecticGriffin left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM in general, I threw in a few comments here and there, but I don't have an amazing handle on relay and the existing infrastructure so don't take anything I say too seriously.

Think this is good to go pending approval from someone other than me!

Comment on lines +451 to +456
let __max :{data_type} = {data.id.name}[0][0];
for (let __i: ubit<{index_size0}> = 0..{size0}) {{
for (let __j: ubit<{index_size1}> = 0..{size1}) {{
if ({data.id.name}[__i][__j] > __max) {{ __max := {data.id.name}[__i][__j]; }}
}}
}}
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

A general (and unhelpful) comment, but this is a good example of what I'm thinking so I'll leave it here.

I get nervous when we have situations where there are load-bearing strings and am wondering if at some point it would be possible to refactor into a nice set of constructors. Though that would likely require having either an internal representation of Dahlia or a Dahlia python library. Obviously this isn't actionable in the short term nor in the scope of this PR, so please don't worry about it.

Copy link
Collaborator Author

@cgyurgyik cgyurgyik May 12, 2021

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Same page. The entire dahlia_impl.py file hurts my eyes; unfortunately I am also the one to blame.

For context, when we first started this in the fall, our goal was to simulate a net using Calyx. In an ideal world, all of our Relay call nodes would be implemented in Verilog or Calyx... hopefully one day that can actually be the case. For now, we decided using Dahlia to implement the function and then lower it to Calyx would be a more efficient process.

While outside the scope of this review, the next question is what are the steps to make this easier to maintain and read. Possibilities:

  1. Python AST for Dahlia. Perhaps a good intermediary step, but still keeps Dahlia in the picture (part of the reason I've been hesitant to make any significant changes to this file for now).
  2. Use Python scripts to generate the correct Calyx component for each Relay call node (similar to the exp generator). Adrian mentions a cleaner way to do this here.
  3. SystemVerilog implementations of the Relay call nodes.

Copy link
Collaborator

@sgpthomas sgpthomas left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM! If there are new python libraries needed to get the ONNX net stuff working, we should document that.

@cgyurgyik
Copy link
Collaborator Author

cgyurgyik commented May 13, 2021

LGTM! If there are new python libraries needed to get the ONNX net stuff working, we should document that.

Added to the Relay frontend docs.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
C: fud Calyx Driver C: Relay Relay-to-FuTIL compiler
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Testing the Relay frontend against a developed infrastructure.
4 participants