]> rtime.felk.cvut.cz Git - pes-rpp/rpp-test-sw.git/blob - commands/cmd_sdram.c
Move commands to toplevel directory (outside of lib)
[pes-rpp/rpp-test-sw.git] / commands / cmd_sdram.c
1 /*
2  * Copyright (C) 2012-2013 Czech Technical University in Prague
3  *
4  * Created on: 28.2.2013
5  *
6  * Authors:
7  *     - Michal Horn
8  *     - Carlos Jenkins <carlos@jenkins.co.cr>
9  *
10  * This program is free software; you can redistribute it and/or modify
11  * it under the terms of the GNU General Public License as published by
12  * the Free Software Foundation; either version 2 of the License, or
13  * (at your option) any later version.
14  *
15  * This program is distributed in the hope that it will be useful,
16  * but WITHOUT ANY WARRANTY; without even the implied warranty of
17  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
18  * GNU General Public License for more details.
19  *
20  * You should have received a copy of the GNU General Public License
21  * along with this program.  If not, see <http://www.gnu.org/licenses/>.
22  *
23  * File : cmd_sdram.c
24  *
25  * Abstract:
26  *      This file contains commands for testing external SDRAM of RPP board.
27  *
28  */
29
30 #include "cmd_sdram.h"
31
32 #ifndef DOCGEN
33
34 #include "rpp/rpp.h"
35 #include <stdlib.h>
36
37 #define BASE_FREQ_MILLIS        1000
38 #define FREQ_VARIABILITY        100
39 #define TEST_TASK_PRIORITY      0
40 #define TEST_TASK_STACK         512
41 #define INPUT_IDLE                      50
42
43
44 // Task control
45 extern xSemaphoreHandle rpp_sdr_cmdproc_semaphore;
46 static boolean_t stop_tasks = FALSE;    /**< Flag for stopping all related tasks. */
47 static uint8_t tasks_running = 0;               /**< Task counter - incremented each time task is spawn, decremented when task is deleted */
48
49 /**
50  * @brief Set flag for tasks to finish.
51  *
52  * All tasks are reading the flag during their work and when
53  * they detect this flag is up, they stop the routine, decrement
54  * task counter and delete themselves.
55  */
56 static void wait_tasks_to_finish()
57 {
58     stop_tasks = TRUE;
59     while(tasks_running > 0) {
60         taskYIELD();
61     }
62     stop_tasks = FALSE;
63 }
64
65 /**
66  * @brief Wait for user input "q" to quit the loop.
67  */
68 void wait_for_quit()
69 {
70     while(rpp_sci_getc() < 0) {
71         vTaskDelay(INPUT_IDLE / portTICK_RATE_MS);
72     }
73 }
74
75
76 /**
77  * FreeRTOS Task that send some noise to the log from time to time.
78  */
79 void sdr_test_task(void* par)
80 {
81     // Calculate wait time in OS ticks
82     static const portTickType freq_ticks = BASE_FREQ_MILLIS / portTICK_RATE_MS;
83     portTickType last_wake_time = xTaskGetTickCount();
84
85     // Initialize rand
86     srand(2097925); // They are random, I swear xD
87
88     uint32_t i = 0;
89     uint32_t variation = 0;
90     int8_t plus_minus = 1;
91     while(!stop_tasks) {
92
93         // Put something in the log
94         rpp_sdr_printf((const char*)
95                 "This is the noise generator at iteration %d "
96                 "putting some noise value %d.", i, rand()
97             );
98         i++;
99
100         if(!stop_tasks) {
101             variation = freq_ticks +
102                     (plus_minus * ((rand() % FREQ_VARIABILITY) + 1));
103             plus_minus = plus_minus * -1;
104             vTaskDelayUntil(&last_wake_time, variation);
105         }
106     }
107
108     // Delete myself
109     tasks_running--;
110     vTaskDelete(NULL);
111 }
112
113 /**
114  * SDR Test entry point.
115  */
116 void test_sdr()
117 {
118     /// Configure module
119     // - See note below.
120
121
122     /// Spawn tasks
123     xTaskHandle test_task_handle;
124
125     // Spawn noise task first, and later enable logging. Depending on the time
126     // required the first logs might not be registered, but that's ok, is better
127     // to check if logging could be enabled after data is being sent that enable
128     // command processor (which output messages to the SCI), and that inmediatly
129     // after the noise task could not be created, forcing to close the just
130     // opened command processor.
131     portBASE_TYPE task_created = xTaskCreate(sdr_test_task,
132                     (const signed char*)"sdr_test_task",
133                     TEST_TASK_STACK, NULL, TEST_TASK_PRIORITY,
134                     &test_task_handle
135             );
136
137     if(task_created != pdPASS) {
138
139         rpp_sci_printf((const char*)
140                 "ERROR: Problem spawning the test task. "
141                 "Error code: %d\r\n", (uint32_t)task_created
142             );
143
144         wait_for_quit();
145         return;
146     }
147     tasks_running++;
148
149     if(rpp_sdr_setup(TRUE) != SUCCESS) {
150         rpp_sci_printf((const char*)
151                 "ERROR: Problem enabling the logging module. "
152             );
153         wait_for_quit();
154         wait_tasks_to_finish();
155         return;
156     }
157
158     // Wait for the SDR included command processor to finish
159     xSemaphoreTake(rpp_sdr_cmdproc_semaphore, portMAX_DELAY);
160     wait_tasks_to_finish();
161
162     /// Reset module configuration
163     if(rpp_sdr_setup(FALSE) != SUCCESS) {
164         rpp_sci_printf((const char*)
165             "ERROR: Could not stop logging module.\r\n"
166         );
167         wait_for_quit();
168     }
169
170     rpp_sci_printf((const char*)"\r\n");
171
172     return;
173 }
174
175
176 /**
177  * @brief Start SDR test routine
178  *
179  * Command syntax: testslog
180  *
181  * @param[in]   cmd_io  Pointer to IO stack
182  * @param[in]   des             Pointer to command descriptor
183  * @param[in]   param   Parameters of command
184  * @return always 0
185  */
186 int cmd_do_test_log(cmd_io_t *cmd_io, const struct cmd_des *des, char *param[]) {
187         test_sdr();
188         return 0;
189 }
190
191 /**
192  * @brief       Tests the capacity and fitness of connected SDRAM
193  *
194  * Command syntax: testsdram
195  *
196  * @param[in]   cmd_io  Pointer to IO stack
197  * @param[in]   des             Pointer to command descriptor
198  * @param[in]   param   Parameters of command
199  * @return      0 when OK or error code
200  */
201 int cmd_do_test_ram(cmd_io_t *cmd_io, const struct cmd_des *des, char *param[]) {
202         volatile uint32_t* addrPtr = (uint32_t*)0x80000000U;
203         volatile uint32_t* endAddr = (uint32_t*)0x83FFFFFFU;
204         uint32_t pattern = 0x55555555U;
205         uint32_t cnt = 0;
206         uint32_t errCnt = 0;
207         uint32_t readVal = 0;
208
209         while (addrPtr <= endAddr) {
210                         *addrPtr = pattern;
211                         pattern += 0x55555555U;
212                         addrPtr++;
213         }
214
215         addrPtr = (uint32_t *)0x80000000U;
216         pattern = 0x55555555U;
217         while (addrPtr <= endAddr) {
218                 readVal = *addrPtr;
219                 if (pattern == readVal) cnt++;
220                 else if(errCnt++ <= 10) {
221                         rpp_sci_printf("Error at %h\r\n",addrPtr);
222                 }
223                 else break;
224                 pattern += 0x55555555U;
225                 addrPtr++;
226         }
227
228         cnt = cnt * sizeof(uint32_t) / 1024 / 1024;
229         if (cnt == 0) {
230                 rpp_sci_printf("SDRAM not connected.");
231         }
232         else {
233                 rpp_sci_printf("SDRAM installed: %d MB", cnt);
234         }
235
236         return 0;
237 }
238
239 #endif  /* DOCGEN */
240
241 /** Command descriptor for test SDRAM */
242 cmd_des_t const cmd_des_test_sdram={
243     0, 0,
244     "testsdram","Test if SDRAM module is connected and if it is, measure capacity",
245     "=== Description ===\n"
246     "\n"
247     "This command tests while SDRAM address space by writing and reading a\n"
248     "pattern. It detects valid SDRAM capacity.\n"
249     "\n"
250     "=== Command syntax ===\n"
251     "\n"
252     "   --> testsdram\n",
253     CMD_HANDLER(cmd_do_test_ram), (void *)&cmd_list_sdram
254 };
255
256 /** Command descriptor for test log to SDRAM */
257 cmd_des_t const cmd_des_test_log={
258     0, 0,
259     "testlog","Open command subprocessor for managing SDRAM logging.",
260     "\n",
261     CMD_HANDLER(cmd_do_test_log), (void *)&cmd_list_sdram
262 };
263
264 /** List of commands for sdram, defined as external */
265 cmd_des_t const *cmd_list_sdram[]={
266         &cmd_des_test_sdram,
267         &cmd_des_test_log,
268         NULL
269 };