해결된 질문
작성
·
468
·
수정됨
1
안녕하세요 좋은 자료로 많은 공부를 하고있습니다.
제가 초보라 초보적인 질문임을 용서해주세요
강의자료 45/98 SPI Master -4 부분을 보면
125 LINES: SCK_CNT==FRQ ? 1'B0:SCK_CNT+1'B1;
133 LINES: SCK_CNT==10'B0 > SCK_INDEX+1'B1:SCK_INDEX;
라고 되어있는데요
강사님께서 의도하시는 바는 SCK_CNT==FREQ 에서 0을 만들고 동시에 SCK_CNT ==0이 되니까 SCK_INDEX 값을 하나 증가 시키고 싶은건 알겠는데요.
두 해당 블럭이 각기 ALWAYS 문 안에 있어서 f/f이면 클락이 있을때 동시에 두 블럭이 동작하면 아래 130-134 LINES의 블럭은 SCK_CNT ==0이 되기 전에 벌써 판단을 함으로 SCK_INDEX +1 동작이 한 클락 뒤에 이루어 지는게 아닌가요? 원래는 동시에 이루어 지고 싶은 의도이나...
동일한 질문 선상에서
라인 141을 보시면 S_READY & READY_CNT==10'D0을 비교하는데요 이도 마찬가지로 의도는 S_READY 상태가 되면 0을 출력하겠다는 의도로 해석됩니다. 그런데 112 라인에서 더 빠르게 동작하여 READY_CNT값이 먼저 1이 증가하면 141 라인은 동작이 불가한거 아닌가 하는 복잡한 생각이 들어 혼란스럽습니다
저런 문제는 걱정 안해도 되는 것인지 궁금합니다. 실제 로직을 구현하고 클락이 빨라지면 문제가 될 것 같기도 한데 혹시 저런것도 다 염두해 두고 로직을 설계해야하는것인지 FPGA를 시작하는 아기로써 겁먹고 문의드립니다.
답변 3
1
1
안녕하세요.
verilog를 배울 때 기본 개념을 알고 있어야 합니다.
spi_master 모듈은 모두 같은 clock domain에서 동작합니다. 모든 always 문 안에는 동일하게 "posedge clock"을 사용하고 있습니다.
verilog는 순차적으로(sequential) 동작하지 않습니다. verilog는 병렬로(parallel), 또는 동시에(synchronous) 동작합니다.
spi_master 모듈 안에 있는 모든 always 문은 동시에, 병렬로 동작합니다.
125 라인이 동작한 후에 133라인이 동작한다는 생각은 잘못된 생각입니다.
125 라인과 133 라인은 동시에, 병렬로 동작합니다.
라인 122 - 127 라인은 매 clock의 상승 에지 마다 sck_cnt 값을 0 ~ freq 까지 증가합니다.
라인 129 - 134 라인은 매 clock의 상승 에지 마다, sck_cnt 값을 살펴보고, sck_cnt 값이 0 일 때, 값을 증가 시킵니다.
이를 좀 더 자세히 살펴보면,
sck_cnt 값이 0 인 순간을 보겠습니다.
sck_cnt 값이 0 이면 다음 clock에 sck_cnt 값은 1 이 됩니다.
sck_cnt 값이 0 이면 다음 clock에 sck_index 값은 1 증가하게 됩니다.
그 다음 clock 에, sck_cnt 값이 1 일 때에는
sck_cnt 값이 2 가 됩니다.
sck_index 값은 sck_cnt 값이 0 이 아니므로 자신의 값을 유지하게 됩니다.
verilog는 이렇게 동작합니다.
라인이 앞에 있다고 먼저 수행하는 것이 아니라,
라인의 위치와 상관 없이 같은 clock domain에 있는 모든 always 문은 동시에 동작합니다.
그리고 마지막으로 조언을 해 드리면,
verilog는 눈으로 보면서 공부하는 것이 아닙니다.
직접 따라서 코딩해 보고, 결과는 simulation 으로 확인해야 합니다.
개발 경력 20년이 넘는 저도 spi_master 구현하려면 수십번 코딩하고 simulation으로 확인하고,
또 수정하고 simulation으로 확인하고 이러한 과정을 거칩니다.
verilog를 눈으로 보면서 공부하려고 한다면 그냥 포기하는게 낫습니다.
눈으로 보면 아무리 해도 이해가 안됩니다. 질문이 꼬리에 꼬리를 물고,
verilog, fpga를 공부하려고 마음 먹으셨다면,
툴부터 설치해서 강의에 있는 내용대로 그대로 코딩하고 simulation으로 결과 확인하시길 바랍니다.
2~3번 정도 반복해서 강의대로 하다 보면 자연스럽게 실력이 느는 날이 옵니다.
감사합니다.
Timing 관련 내용입니다.
fpga는 기본적으로 툴에서 Timing을 맞추어 줍니다. Implemenation 과정에서 타이밍을 맞추어 줍니다. 그러나 1-clock안에 처리하지 못하는 경우가 있습니다. Timing violation 이 발생하는 경우입니다. 이런 경우에는 에러를 확인해서 Timing violation이 발생하는 부분을 수정해 주어야 합니다. 예를 들면 1-clock 안에 처리할 수 없는 경우에는 2-clock 으로 나누어서 처리를 합니다. 1-clock 안에 처리되는 내용을 2-clock으로 나누어 처리하게 된다면, 이로 인해 연관된 모든 부분의 Timing을 맞추어 주어야 합니다. 따라서 코딩할 때, Timing vioation이 발생하지 않는 코드를 구현하는 것이 중요합니다.
본 강의에 설명된 모든 코드들은 Timing violation이 발생하지 않는 코드입니다.
비교문 1~2개 정도는 시간이 많이 소요되지는 않습니다. 경험에 의하면 비교문 4~5개 까지(bits 수에 따라 달라질 수 있습니다)는 1-clock 안에 처리됩니다. 물론 main clock 주파수, 사용하는 fpga 종류등 경우에 따라 달라지는 요소들이 많이 있습니다. 이는 경험적으로 얻게 되는 지식입니다.
0
안녕하세요 강사님
빠른 답변과 정성스런 답변에 감사드립니다.
그런데 제가 질문을 더 상세히 잘 하지 못한거 같아 의미가 잘못 전달 된건 같습니다.
저의 질문은 verilog를 통해 저희가 설계하는건 최종 회로이고 어쨋든 이상적이지 않으므로 변경 또는 값이 업데이트 되는데 실제 회로에서 다소 시간이 걸리는 것으로 알고있습니다.
그러면, 병렬로 신호가 처리 될 텐데요.
회로 1은 클락이 있을때 sck_cnt를 0에서 1로 증가시키고
회로 2는 클락이 있을때 sck_index 값은 sck_cnt를 모니터 하며 값을 변경할 것입니다.
추가적으로 비교 동작은 어쨋든 추가 회로 LUT가 맞으려나요... 그걸 통해서 비교를 함으로 다소 더 시간이 걸리는 것으로 경험한 적이 있습니다.
그렇다면, 원하는건 동시 동작이지만 회로 2가 클락이 있어 sck_cnt를 모니터 하는 시점에서는 벌써 sck_cnt가 증가되어 있어 혹시 오류가 생기지 않을까 하는 질문이었습니다.
요것만 경험이 많으신 강사님이 확인해주시면 더 공부하도록 하겠습니다.
정성스런 답변에 정말 정말 감사드립니다.