diff --git a/report/.gitignore b/report/.gitignore new file mode 100644 index 0000000..39016dc --- /dev/null +++ b/report/.gitignore @@ -0,0 +1,7 @@ +# TeX auxiliary files +*.aux +*.log +*.out +*.synctex.gz + +_minted-report/ diff --git a/report/img/ConsoleOutput.png b/report/img/ConsoleOutput.png new file mode 100644 index 0000000..04a9e14 Binary files /dev/null and b/report/img/ConsoleOutput.png differ diff --git a/report/report.pdf b/report/report.pdf new file mode 100644 index 0000000..c298096 Binary files /dev/null and b/report/report.pdf differ diff --git a/report/report.tex b/report/report.tex new file mode 100644 index 0000000..adbc891 --- /dev/null +++ b/report/report.tex @@ -0,0 +1,344 @@ +% +% !TEX TS-program = xelatex +% !TEX encoding = UTF-8 Unicode +% !TEX spellcheck = el-GR +% +% Low-Level HW Digital Systems II coursework report +% +% +% authors: +% Χρήστος Χουτουρίδης ΑΕΜ 8997 +% cchoutou@ece.auth.gr + + +% Options: +% +% 1) mainlang= +% Default: english +% Set the default language of the document which affects hyphenations, +% localization (section, dates, etc...) +% +% example: \documentclass[mainlang=greek]{AUThReport} +% +% 2) +% Add hyphenation and typesetting support for other languages +% Currently supports: english, greek, german, frenc +% +% example: \documentclass[english, greek]{AUThReport} +% +% 3) short: Requests a shorter title for the document +% Default: no short +% +% example: \documentclass[short]{AUThReport} +% +\documentclass[a4paper, 11pt, mainlang=greek, english]{AUThReport} + +\CurrentDate{\today} + +% Greek report document setup suggestions +%--------------------------------- +% Document configuration +\AuthorName{Χρήστος Χουτουρίδης} +\AuthorAEM{8997} +\AuthorMail{cchoutou@ece.auth.gr} + +%\CoAuthorName{CoAuthor Name} +%\CoAuthorAEM{AEM} +%\CoAuthorMail{CoAuthor Mail} + +% \WorkGroup{Ομάδα Χ} + +\DocTitle{Εργασία} +\DocSubTitle{Πολλαπλασιασμός αριθμών κινητής υποδιαστολής} + +\Department{Τμήμα ΗΜΜΥ. Τομέας Ηλεκτρονικής} +\ClassName{Ψηφιακά Συστήματα HW σε Χαμηλά Επίπεδα Λογικής II} + +\InstructorName{Βασίλης Παυλίδης} +\InstructorMail{ } + +\CoInstructorName{Ευάγγελος Τζουβάρας} +\CoInstructorMail{ } + + +% Local package requirements +%--------------------------------- +%\usepackage{tabularx} +%\usepackage{array} +%\usepackage{commath} + +\usepackage{amsmath, amssymb, amsfonts} +\usepackage{graphicx} +\usepackage{subcaption} +\usepackage{float} + + +% Requires: -shell-escape compile argument +\usepackage{minted} +\usepackage{xcolor} + +\newminted{verilog}{ + fontsize=\small, + breaklines, + autogobble, + %frame=lines, + %framesep=5pt, + baselinestretch=1.1, + tabsize=2, + %bgcolor=LightGray, + numbersep=8pt, + gobble=0 +} + +\newcommand{\icode}[1]{\mintinline{verilog}{#1}} + + +\newcommand{\repo}{https://git.hoo2.net/hoo2/HWDigSys-II} +\newcommand{\repoNopipeline}{https://git.hoo2.net/hoo2/HWDigSys-II/src/branch/no-pipeline} +\begin{document} + +% Request a title page or header +\InsertTitle + +\section{Εισαγωγή} + +Η παρούσα εργασία αφορά στην υλοποίηση ενός πολλαπλασιαστή αριθμών κινητής υποδιαστολής μονής ακρίβειας (IEEE-754 single-precision) σε γλώσσα περιγραφής υλικού SystemVerilog. +Η σχεδίαση του κυκλώματος ακολουθεί μια αρθρωτή και κλιμακούμενη προσέγγιση, βασισμένη σε δομή pipeline τριών σταδίων. +Το κύριο ζητούμενο ήταν η διαχωρισμένη υλοποίηση της κανονικοποίησης, της στρογγυλοποίησης και της διαχείρισης εξαιρέσεων, με δυνατότητα ελέγχου διαφορετικών τρόπων στρογγυλοποίησης. +\par +Στόχος της εργασίας είναι η κατανόηση της εσωτερικής λειτουργίας των αριθμητικών μονάδων κινητής υποδιαστολής, η υλοποίηση τους σε επίπεδο RTL και η επαλήθευση της σωστής λειτουργίας τους μέσω εκτενούς ελέγχου με test benches. +Η εργασία απαιτεί κατανόηση τόσο της γλώσσας SystemVerilog όσο και του προτύπου IEEE-754, και συνδυάζει αρχιτεκτονική σχεδίαση, ψηφιακή λογική και επαλήθευση μέσω προσομοίωσης. + +\subsection{Παραδοτέα} +Τα παραδοτέα της εργασίας αποτελούνται από: +\begin{itemize} + \item Την παρούσα αναφορά. + \item Τον κατάλογο \textbf{src/}, που περιέχει τον κώδικα της SystemVerilog με τα ζητηθέντα modules. + \item Τον κατάλογο \textbf{sim/}, που περιέχει το ζητηθέν test bench αλλά και επιμέρους tests για τα υπόλοιπα modules (πλην του exception handler). + \item Το \href{\repo}{σύνδεσμο} με το αποθετήριο που περιέχει όλο το project στο vsim, τους κώδικες της SystemVerilog και της αναφοράς καθώς και τα παραδοτέα. +\end{itemize} +Στην εργασία \textbf{δεν} υλοποιήθηκαν τα εξής: +\begin{itemize} + \item \textit{Όλοι οι 144} συνδυασμοί των corner cases για το test bench με βάση τους τυχαίους αριθμούς και τον έλεγχο μέσω multiplication.sv. + Αντ' αυτού δημιουργήθηκαν test cases που ελέγχουν τόσο την “κανονική” λειτουργία όσο και αρκετά corner cases αλλά οι τιμές τους εισήχθηκαν \textit{με το χέρι}. + \item Το μέρος με τα \textit{immediate assertions}. +\end{itemize} + +\section{Προσέγγιση Υλοποίησης} +Για την εργασία χρησιμοποιήσαμε μια \textbf{αρθρωτή} προσέγγιση. +Καθώς η πολυπλοκότητα έμοιαζε αρκετά μεγάλη, σε συνδυασμό με τη μικρή προσωπική εμπειρία σε ψηφιακή σχεδίαση με verilog, προτιμήσαμε να ακολουθήσουμε μια \textbf{test driven} προσέγγιση ανά module. +Έτσι χωρίσαμε την ανάπτυξη στα modules που πρότεινε η εκφώνηση και για αυτά δημιουργήσαμε test benches. +Τα βασικά tests που θα χρειαζόταν να υλοποιηθούν πρώτα ήταν για τα \textit{normalize} και \textit{round}. +Το \textit{exception handler} θα μπορούσε να εκμαιευτεί με “αφαίρεση” των παραπάνω από το συνολικό test bench του \textit{fp\_mult}. +Όλα αυτά τα αρχεία μπορούν να βρεθούν στον κατάλογο \textit{sim/}. +\par +Τα test αυτά αν και κάπως τετριμμένα, έπαιξαν πολύ σημαντικό ρόλο στην υλοποίηση καθώς μας δώσανε τη δυνατότητα να χωριστούν τα interfaces των modules και να πιστοποιήσουν ότι η αναγκαία λειτουργικότητα είναι παρούσα. +Κάτι που φυσικά μας βοήθησε στην απομόνωση των σφαλμάτων κλπ... +\par +Έχοντας υλοποιήσει λοιπόν τα test προβήκαμε στην υλοποίηση των ίδιων των modules. +Αρχικά υλοποιήσαμε τα \textit{normalize} και \textit{round} και έπειτα το \textit{fp\_mult}. +Με αυτά τα τρία να περνούν τα επιμέρους tests προχωρήσαμε στην υλοποίηση του \textit{exception handler}. +Για αυτό το module δεν υλοποιήσαμε πρώτα tests καθώς υπήρχαν τα συνολικά tests και το μόνο modul-άκι που “άλλαζε” ήταν αυτό. +\par +Τέλος με όλη τη λειτουργικότητα έτοιμη, προβήκαμε στην τελευταία αλλαγή, που ήταν η μετατροπή της λογικής για χρήση \textbf{pipeline τριών σταδίων}. +Μιας και τα αρχεία για τα tests για το pipeline είναι διαφορετικά από τα αρχικά, ο αναγνώστης μπορεί \href{\repoNopipeline}{εδώ} να βρει αυτή την ενδιάμεση έκδοση. + +\subsection{Pipeline} + +Η αρχική υλοποίηση όπως είδαμε είχε combinational logic. +Επομένως το αποτέλεσμα του πολλαπλασιασμού θα ήταν διαθέσιμο σε κάθε clock του ρολογιού του \textit{fp\_mult\_top}. +Παρόλα αυτά ο διαχωρισμός σε 3 στάδια μειώνει αρκετά το βάθος, χωρίς να μεγαλώνει την ανάγκη για extra clock ticks. +Αντ' αυτού μειώνει το συνολικό latency. +Τα στάδια που χρησιμοποιήθηκαν είναι με τη σειρά τα εξής: +\begin{enumerate} + \item \textbf{Normalize}: Όπου καλείται το normalize\_mult. + \item \textbf{Round}: Όπου καλείται το round\_mult και το + \item \textbf{Exception handler}: Όπου καλείται το exception\_mult +\end{enumerate} +\par +Για το pipeline εργαστήκαμε με γνώμονα τη διατήρηση όλης της απαραίτητης πληροφορίας στα στάδια, ούτως ώστε ο χρήστης να μπορεί σε κάθε clock να τροφοδοτεί το module με διαφορετικούς αριθμούς για πολλαπλασιασμό. +Όλα τα σήματα από την είσοδο τροφοδοτούνται από το ένα στάδιο στο επόμενο. +Η μετάδοση αυτή σταματάει μόνο αν τα σήματα δεν είναι απαραίτητα για τη λειτουργία του επόμενου module. +Με αυτό τον τρόπο για παράδειγμα όλη η απαραίτητη πληροφορία για το κάθε module, περνάει από το ένα στάδιο στο επόμενο σε κάθε clock. +Για την ακρίβεια, μετά τον αρχικό υπολογισμό του πρόσημου καθώς και του αποτελέσματος του πολλαπλασιασμού για τον εκθέτη και τη mantissa: +\begin{itemize} + \item Οι \textbf{αριθμοί} προς πολλαπλασιασμό φτάνουνε μέχρι τον exception handler. + \item Ο \textbf{εκθέτης} και η \textbf{mantissa} φτάνει μέχρι τον exception handler, όπου και συνθέτει τον τελικό αριθμό πριν την είσοδο. + \item To υπολογισμένο \textbf{πρόσημο} του τελικού αριθμού φτάνει μέχρι το round module. + \item Τα \textbf{guard} και \textbf{sticky} bits φτάνουν από το normalize μέχρι το round module. + \item To \textbf{inexact} bit από το round μέχρι το exception handler. +\end{itemize} +\par +Ενώ επιλέξαμε να υποστηρίξουμε με pipeline όλη σχεδόν την πληροφορία, ένα σήμα δεν ακολουθεί την οδό των σταδίων. +Πρόκειται για το \textbf{round}. +Ενώ για τα υπόλοιπα θεωρήσαμε πως ο χρήστης πρέπει να μπορεί να τα αλλάζει σε κάθε clock του ρολογιού, αυτό υποθέσαμε ότι θα επιλέγεται κατά την έναρξη και θα \textbf{παραμένει αμετάβλητο κάθ' όλη τη διάρκεια λειτουργίας}. +Για το λόγο αυτό, δεν χρειάστηκε να το “περάσουμε” από τα στάδια. + +\section{Λεπτομέρειες Υλοποίησης} + +\subsection{\texttt{fp\_mult.sv} --- Floating Point Multiplier (Top Module)} + +Το module \texttt{fp\_mult} υλοποιεί έναν πλήρως καταχωρημένο πολλαπλασιαστή αριθμών κινητής υποδιαστολής μονής ακρίβειας (IEEE-754). +Αποτελείται από ένα pipeline 3 σταδίων: + +\begin{itemize} + \item \textbf{Stage 0 (Decode)}: + Εξάγει πρόσημο, εκθέτες και mantissas από τις εισόδους \texttt{a}, \texttt{b}. + Υπολογίζει το αρχικό γινόμενο mantissas και το bias-adjusted εκθέτη. + Η λειτουρία αυτή βρίσκεται σε ένα section με combinational logic. + \begin{verilogcode} + sign = a[31] ^ b[31]; + exp_a = a[30:23]; + exp_b = b[30:23]; + s0_exponent = exp_a + exp_b - 127; + + mant_a = (exp_a == 0) ? {1'b0, a[22:0]} : {1'b1, a[22:0]}; + mant_b = (exp_b == 0) ? {1'b0, b[22:0]} : {1'b1, b[22:0]}; + s0_mantissa = mant_a * mant_b; + \end{verilogcode} + \item \textbf{Stage 1 (Normalize)}: + Κανονικοποιεί το αποτέλεσμα, προσαρμόζοντας την mantissa και τον εκθέτη. + Παράγει επίσης guard και sticky bits για στρογγυλοποίηση. + \item \textbf{Stage 2 (Round)}: + Εφαρμόζει τον επιλεγμένο τρόπο στρογγυλοποίησης και υπολογίζει την τελική mantissa και εκθέτη καθώς και το σήμα inexact. + \item \textbf{Stage 3 (Exception Handling)}: + Εντοπίζει καταστάσεις όπως NaN, infinities, overflow/underflow, μηδενικά και υπολογίζει την τελική έξοδο \texttt{z} και το flag \texttt{status}. + \end{itemize} + +Υποστηρίζει ασύγχρονη επαναφορά (\texttt{rst}) και συγχρονισμό μέσω ρολογιού (\texttt{clk}). + +\subsection{\texttt{normalize\_mult.sv} --- Normalize Stage} + +Το module αυτό δέχεται ένα 48-bit mantissa και έναν 10-bit εκθέτη. Ελέγχει εάν χρειάζεται shift για κανονικοποίηση της mantissa (ώστε να ξεκινά από MSB=1) και αντίστοιχα προσαρμόζει τον εκθέτη. + +\begin{itemize} + \item \texttt{mantissa\_out}: Κανονικοποιημένη mantissa (23 bits) + \item \texttt{guard\_bit, sticky\_bit}: Χρήσιμα για την ακρίβεια στη στρογγυλοποίηση + \item \texttt{exponent\_out}: Νέος εκθέτης μετά την κανονικοποίηση +\end{itemize} + +\subsection{\texttt{round\_mult.sv} --- Round Stage} + +Το module εφαρμόζει έναν από τους υποστηριζόμενους τρόπους στρογγυλοποίησης σύμφωνα με το IEEE-754 standard: + +\begin{itemize} + \item Round to Nearest Even + \item Round Toward Zero + \item Round Toward $\inf$ + \item Round Toward $-\inf$ + \item Near-Up + \item Away from Zero +\end{itemize} + +Για κάθε διαφορετικό mode με βάση το round υλοποιεί διαφορετική προσέγγιση. +Για παράδειγμα για IEEE nearest\ event έχουμε: +\begin{verilogcode} + if (guard_bit && (sticky_bit || mantissa_extended[0])) begin + mantissa_rounded = mantissa_extended + 1; + end +\end{verilogcode} +Ενώ για IEEE pinf: +\begin{verilogcode} + if (!sign_in && (guard_bit | sticky_bit)) begin + mantissa_rounded = mantissa_extended + 1; + end +\end{verilogcode} +Η υλοποίηση των modes έγινε με διαφορετικές συναρτήσεις, μέσα στο module. +Οι είσοδοι περιλαμβάνουν την mantissa, τον εκθέτη, το πρόσημο και τα bits \texttt{guard} και \texttt{sticky}. +Οι έξοδοι είναι η νέα mantissa και ο εκθέτης μετά τη στρογγυλοποίηση, καθώς και το σήμα \texttt{inexact}. + +\subsection{\texttt{round\_modes.sv} --- Round Mode Helpers} + +Ορίζει ένα enumeration τύπο \texttt{round\_mode\_t} για τους 6 υποστηριζόμενους τρόπους στρογγυλοποίησης, που χρησιμοποιούνται κυρίως κατά τον χειρισμό overflow και underflow στην εξαίρεση. +\begin{verilogcode} + typedef enum logic [2:0] { + RND_IEEE_NEAREST_EVEN = 3'd0, + RND_IEEE_ZERO = 3'd1, + RND_IEEE_PINF = 3'd2, + RND_IEEE_NINF = 3'd3, + RND_NEAR_UP = 3'd4, + RND_AWAY_ZERO = 3'd5 + } round_mode_t; +\end{verilogcode} + +\subsection{\texttt{exception\_mult.sv} --- Exception Handling} + +Αυτό το module χειρίζεται corner cases και ειδικές τιμές: + +\begin{itemize} + \item Ανίχνευση και χειρισμός NaNs, infinities, zero + \item Overflow/underflow μετά τη στρογγυλοποίηση + \item Ορισμός της τελικής τιμής \texttt{z} + \item Ορισμός των status flags: \texttt{zero\_f}, \texttt{inf\_f}, \texttt{nan\_f}, \texttt{tiny\_f}, \texttt{huge\_f}, \texttt{inexact\_f} +\end{itemize} + +Χρησιμοποιεί ένα \texttt{enum interp\_t} για την κατηγοριοποίηση αριθμών (ZERO, INF, NORM, MIN\_NORM, MAX\_NORM) και δύο συναρτήσεις: +\begin{itemize} + \item \texttt{num\_interp()}: Επιστρέφει το είδος του αριθμού (π.χ., αν είναι infinity ή zero) + \item \texttt{z\_num()}: Επιστρέφει την bitwise αναπαράσταση ενός αριθμού βάσει του είδους του +\end{itemize} + +Η λογική ελέγχει τους συνδυασμούς εισόδων και εφαρμόζει τις κατάλληλες ενέργειες βάσει πίνακα (table 4) και του rounding mode. +Ο βασικός κορμός είναι μια switch case όπου γίνεται το dispatch όλων των corner cases: +\begin{verilogcode} + a_class = num_interp(a); + b_class = num_interp(b); + + case ({a_class, b_class}) + {ZERO, ZERO}, {ZERO, NORM}, {NORM, ZERO}: // ... + {ZERO, INF}, {INF, ZERO}: // ... + {INF, INF}, {NORM, INF}, {INF, NORM}: // ... + default: // {NORM, NORM} ... + endcase +\end{verilogcode} +Ειδικά στο default βρίσκεται η λογική του extra rounding όταν έχουμε NaN, Inf, κλπ. + +\section{Επαλήθευση και Επικύρωση} +Όπως αναφέραμε παραπάνω οι επαλήθευση έγινε σταδιακά. +Σε κάθε αρχείο στον κατάλογο \textit{sim/} υπάρχουν tests που επιβεβαιώνουν την ορθή λειτουργία του κάθε module. +Για να τρέξουμε τα test χρησιμοποιήσαμε το vsim. +Για παράδειγμα για τα test του round\_mult: +\begin{verbatim} + vlog sim/round_mult_tb + vsim -voptargs=+acc work.round_tb + run 200ns +\end{verbatim} +Όλες οι εκτελέσεις εμφανίζουν μηνύματα στην κονσόλα με τα αποτελέσματα. +\par +Τα τελικά tests που ανήκουν στο fp\_mult\_top\_tb έχουν ελέγχους που ακολουθούν κάποια test vectors όπως παρακάτω: +\begin{verilogcode} + initial begin + $display("Starting fp_mult test...\n"); + + // Test cases + tests[0] = '{32'h3f800000, 32'h40000000, 32'h40000000, "+1.0 * +2.0 = +2.0"}; + tests[1] = '{32'h40400000, 32'h40400000, 32'h41100000, "+3.0 * +3.0 = +9.0"}; + tests[2] = '{32'hc0400000, 32'h40400000, 32'hc1100000, "-3.0 * +3.0 = -9.0"}; + tests[3] = '{32'hbf800000, 32'h40000000, 32'hc0000000, "-1.0 * +2.0 = -2.0"}; + // ... + end +\end{verilogcode} +Με βάση αυτά τα vectors, παράγονται μηνύματα που έχουν τη μορφή: +\begin{verbatim} + # [8] +12.34 * -0.0001 = -0.001234 + # A=414570a4 B=b8d1b717 => Z=baa1be2b (expected baa1be2b) PASS +\end{verbatim} +Ένα στιγμιότυπο από την έξοδο φαίνεται στην εικόνα \ref{fig:output}. +\begin{figure}[!ht] + \centering + \includegraphics[width=0.9\textwidth]{img/ConsoleOutput.png} + \caption{Στιγμιότυπο εξόδου.} + \label{fig:output} +\end{figure} + + +\section{Συμπεράσματα} + +Μέσα από την παρούσα εργασία υλοποιήθηκε με επιτυχία μια πλήρως καταχωρημένη αριθμητική μονάδα πολλαπλασιασμού αριθμών κινητής υποδιαστολής, σύμφωνα με το πρότυπο IEEE-754. +Η υλοποίηση με χρήση pipeline τριών σταδίων προσέφερε βελτιωμένη απόδοση και σαφή διαχωρισμό λειτουργιών, καθιστώντας τη σχεδίαση πιο ευέλικτη και επεκτάσιμη. +Ο διαχωρισμός σε modules με αυστηρά ορισμένα interfaces διευκόλυνε την ανάπτυξη και τον έλεγχο των επιμέρους λειτουργιών, ενώ η προσέγγιση βασισμένη σε επαλήθευση (test-driven development) διασφάλισε την ορθότητα κάθε σταδίου. +\par +Αν και δεν καλύφθηκαν όλοι οι δυνατοί συνδυασμοί corner cases, η λογική του κυκλώματος και οι ενδείξεις των αποτελεσμάτων επαληθεύουν ότι η λειτουργία του multiplier είναι σε μεγάλο βαθμό ορθή. +Η εργασία παρείχε μια ουσιαστική εμπειρία στην πρακτική υλοποίηση σύνθετων αριθμητικών μονάδων σε χαμηλό επίπεδο, αναδεικνύοντας τις προκλήσεις αλλά και τις δυνατότητες της σύγχρονης ψηφιακής σχεδίασης. + +\end{document}