/* Application entry point */ int main() { int status = 0; #ifdef ZYNQ7_BAREMETAL SWITCH_TO_SYS_MODE(); #endif /* Initialize HW system components */ init_system(); rsc_info.rsc_tab = (struct resource_table *)&resources; rsc_info.size = sizeof(resources); /* Initialize RPMSG framework */ status = remoteproc_resource_init(&rsc_info, rpmsg_channel_created, rpmsg_channel_deleted, rpmsg_read_cb, &proc); if (status < 0) { return -1; } while (1) { __asm__("wfi\n\t"); } return 0; }
/*-----------------------------------------------------------------------------* * Application entry point *-----------------------------------------------------------------------------*/ int main(void) { int status = 0; /* Create buffer to send data between RPMSG callback and processing task */ buffer_create(); /* Initialize HW and SW components/objects */ init_system(); /* Resource table needs to be provided to remoteproc_resource_init() */ rsc_info.rsc_tab = (struct resource_table *)&resources; rsc_info.size = sizeof(resources); /* Initialize OpenAMP framework */ status = remoteproc_resource_init(&rsc_info, rpmsg_channel_created, rpmsg_channel_deleted, rpmsg_read_cb, &proc); if (RPROC_SUCCESS != status) { /* print directly on serial port */ xil_printf("Error: initializing OpenAMP framework\n"); } else { mat_mul_demo(); } while (1) { __asm__("wfi\n\t"); } /* suppress compilation warnings*/ return 0; }
static void mat_mul_demo(void *unused_arg) { int status = 0; (void)unused_arg; /* Create buffer to send data between RPMSG callback and processing task */ buffer_create(); /* Initialize HW and SW components/objects */ init_system(); /* Resource table needs to be provided to remoteproc_resource_init() */ rsc_info.rsc_tab = (struct resource_table *)&resources; rsc_info.size = sizeof(resources); /* Initialize OpenAMP framework */ status = remoteproc_resource_init(&rsc_info, rpmsg_channel_created, rpmsg_channel_deleted, rpmsg_read_cb, &proc); if (RPROC_SUCCESS != status) { xil_printf("Error: initializing OpenAMP framework\n"); return; } /* Stay in data processing loop until we receive a 'shutdown' message */ while (1) { void *data; int len; /* wait for data... */ buffer_pull(&data, &len); /* Process incoming message/data */ if (*(int *)data == SHUTDOWN_MSG) { /* disable interrupts and free resources */ remoteproc_resource_deinit(proc); /* Terminate this task */ vTaskDelete(NULL); break; } else { env_memcpy(matrix_array, data, len); /* Process received data and multiple matrices. */ Matrix_Multiply(&matrix_array[0], &matrix_array[1], &matrix_result); /* Send result back */ if (RPMSG_SUCCESS != rpmsg_send(app_rp_chnl, &matrix_result, sizeof(matrix))) { xil_printf("Error: rpmsg_send failed\n"); } } } }
void communication_task(){ int status; rsc_info.rsc_tab = (struct resource_table *)&resources; rsc_info.size = sizeof(resources); zynqMP_r5_gic_initialize(); /* Initialize RPMSG framework */ status = remoteproc_resource_init(&rsc_info, rpmsg_channel_created, rpmsg_channel_deleted, rpmsg_read_cb ,&proc); if (status < 0) { return; } #ifdef USE_FREERTOS comm_queueset = xQueueCreateSet( 2 ); xQueueAddToSet( OpenAMPInstPtr.send_queue, comm_queueset); xQueueAddToSet( OpenAMPInstPtr.lock, comm_queueset); #else env_create_sync_lock(&OpenAMPInstPtr.lock,LOCKED); #endif env_enable_interrupt(VRING1_IPI_INTR_VECT,0,0); while (1) { #ifdef USE_FREERTOS QueueSetMemberHandle_t xActivatedMember; xActivatedMember = xQueueSelectFromSet( comm_queueset, portMAX_DELAY); if( xActivatedMember == OpenAMPInstPtr.lock ) { env_acquire_sync_lock(OpenAMPInstPtr.lock); process_communication(OpenAMPInstPtr); } if (xActivatedMember == OpenAMPInstPtr.send_queue) { xQueueReceive( OpenAMPInstPtr.send_queue, &send_data, 0 ); rpmsg_send(app_rp_chnl, send_data.data, send_data.length); } #else env_acquire_sync_lock(OpenAMPInstPtr.lock); process_communication(OpenAMPInstPtr); echo_test(); /* Wait for the result data on queue */ if(pq_qlength(OpenAMPInstPtr.send_queue) > 0) { send_data = pq_dequeue(OpenAMPInstPtr.send_queue); /* Send the result of echo_test back to master. */ rpmsg_send(app_rp_chnl, send_data->data, send_data->length); } #endif } }
/*-----------------------------------------------------------------------------* * Application specific *-----------------------------------------------------------------------------*/ static void rpc_demo(void) { int fd, bytes_written, bytes_read; char fname[] = "remote.file"; char wbuff[50]; char rbuff[1024]; char ubuff[50]; float fdata; int idata; int ret; int status = 0; /* Initialize HW and SW components/objects */ init_system(); env_create_sync_lock(&chnl_cb_flag, LOCKED); /* Resource table needs to be provided to remoteproc_resource_init() */ rsc_info.rsc_tab = (struct resource_table *)&resources; rsc_info.size = sizeof(resources); /* Initialize OpenAMP framework */ status = remoteproc_resource_init(&rsc_info, rpmsg_channel_created, rpmsg_channel_deleted, rpmsg_read_cb, &proc); if (RPROC_SUCCESS != status) { /* print error directly on serial port */ xil_printf("Error: initializing OpenAMP framework\n"); return; } /* wait for notification that will happen on channel creation (interrupt) */ env_acquire_sync_lock(chnl_cb_flag); /* redirect I/Os */ rpmsg_retarget_init(app_rp_chnl, shutdown_cb); printf("\r\nRemote>Baremetal Remote Procedure Call (RPC) Demonstration\r\n"); printf("\r\nRemote>***************************************************\r\n"); printf("\r\nRemote>Rpmsg based retargetting to proxy initialized..\r\n"); /* Remote performing file IO on Master */ printf("\r\nRemote>FileIO demo ..\r\n"); printf("\r\nRemote>Creating a file on master and writing to it..\r\n"); fd = open(fname, REDEF_O_CREAT | REDEF_O_WRONLY | REDEF_O_APPEND, S_IRUSR | S_IWUSR); printf("\r\nRemote>Opened file '%s' with fd = %d\r\n", fname, fd); sprintf(wbuff, "This is a test string being written to file.."); bytes_written = write(fd, wbuff, strlen(wbuff)); printf("\r\nRemote>Wrote to fd = %d, size = %d, content = %s\r\n", fd, bytes_written, wbuff); close(fd); printf("\r\nRemote>Closed fd = %d\r\n", fd); /* Remote performing file IO on Master */ printf("\r\nRemote>Reading a file on master and displaying its contents..\r\n"); fd = open(fname, REDEF_O_RDONLY, S_IRUSR | S_IWUSR); printf("\r\nRemote>Opened file '%s' with fd = %d\r\n", fname, fd); bytes_read = read(fd, rbuff, 1024); *(char*) (&rbuff[0] + bytes_read + 1) = 0; printf( "\r\nRemote>Read from fd = %d, size = %d, printing contents below .. %s\r\n", fd, bytes_read, rbuff); close(fd); printf("\r\nRemote>Closed fd = %d\r\n", fd); while (1) { /* Remote performing STDIO on Master */ printf("\r\nRemote>Remote firmware using scanf and printf ..\r\n"); printf("\r\nRemote>Scanning user input from master..\r\n"); printf("\r\nRemote>Enter name\r\n"); ret = scanf("%s", ubuff); if (ret) { printf("\r\nRemote>Enter age\r\n"); ret = scanf("%d", &idata); if(ret) { printf("\r\nRemote>Enter value for pi\r\n"); ret = scanf("%f", &fdata); if(ret) { printf("\r\nRemote>User name = '%s'\r\n", ubuff); printf("\r\nRemote>User age = '%d'\r\n", idata); printf("\r\nRemote>User entered value of pi = '%f'\r\n", fdata); } } } if(!ret) { scanf("%s", ubuff); printf("Remote> Invalid value. Starting again...."); } else { printf("\r\nRemote>Repeat demo ? (enter yes or no) \r\n"); scanf("%s", ubuff); if((strcmp(ubuff,"no")) && (strcmp(ubuff,"yes"))) { printf("\r\nRemote>Invalid option. Starting again....\r\n"); } else if((!strcmp(ubuff,"no"))) { printf("\r\nRemote>RPC retargetting quitting ...\r\n"); sprintf(wbuff, RPC_CHANNEL_READY_TO_CLOSE); rpmsg_retarget_send(wbuff, sizeof(RPC_CHANNEL_READY_TO_CLOSE) + 1); break; } } } printf("\r\nRemote> Firmware's rpmsg-openamp-demo-channel going down! \r\n"); }
int main() { struct remote_proc *proc; int uninit = 0; struct ept_cmd_data *ept_data; #ifdef ZYNQ7_BAREMETAL /* Switch to System Mode */ SWITCH_TO_SYS_MODE(); #endif /* Initialize HW system components */ init_system(); rsc_info.rsc_tab = (struct resource_table *)&resources; rsc_info.size = sizeof(resources); /* This API creates the virtio devices for this remote node and initializes other relevant resources defined in the resource table */ remoteproc_resource_init(&rsc_info, rpmsg_channel_created, rpmsg_channel_deleted, rpmsg_read_default_cb, &proc); for (;;) { if (intr_flag) { struct command *cmd = (struct command *)r_buffer; if (cmd->comm_start == CMD_START) { unsigned int cm_code = cmd->comm_code; void *data = cmd->data; switch (cm_code) { case CREATE_EPT: ept_data = (struct ept_cmd_data *)data; rp_ept = rpmsg_create_ept(app_rp_chnl, rpmsg_read_ept_cb, RPMSG_NULL, ept_data->dst); if (rp_ept) { /* Send data back to ack. */ rpmsg_sendto(app_rp_chnl, r_buffer, Len, Src); } break; case DELETE_EPT: rpmsg_destroy_ept(rp_ept); rpmsg_sendto(app_rp_chnl, r_buffer, Len, Src); break; case CREATE_CHNL: break; case DELETE_CHNL: rpmsg_sendto(app_rp_chnl, r_buffer, Len, Src); remoteproc_resource_deinit(proc); uninit = 1; break; case QUERY_FW_NAME: rpmsg_send(app_rp_chnl, &firmware_name[0], strlen(firmware_name) + 1); break; default: rpmsg_sendto(app_rp_chnl, r_buffer, Len, Src); break; } } else { rpmsg_sendto(app_rp_chnl, r_buffer, Len, Src); } intr_flag = 0; if (uninit) break; } sleep(); } return 0; }