Re-organized sub-directory by category
[staging/basesystem.git] / service / system / rom_access_library / library / rom / src / ss_sm_ram_access.cpp
1 /*
2  * @copyright Copyright (c) 2016-2020 TOYOTA MOTOR CORPORATION.
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16
17 #include "system_service/ss_sm_ram_access.h"
18 #include <stdio.h>
19 #include <sys/types.h>
20 #include <sys/stat.h>
21 #include <fcntl.h>
22 #include <native_service/cl_lock.h>
23 #include <native_service/cl_lockid.h>
24 #include <stub/el_mem.h>
25 #include "system_service/ss_sm_boot_access.h"
26 #include "ss_rom_access_if_romaccesslibrarylog.h"
27 #include "ss_sm_checksum.h"
28 #include "ss_rom_access_define.h"
29
30
31
32 #define RAM_PATH     "/nv/BS/ss/rom_access_library/rwdata/ramdata.dat"
33 #define RAM_OLD_PATH RAM_PATH".old"
34 static const uint8_t kSigNature[] = { 0xDE, 0xAD, 0xBE, 0xEF };
35 static const uint8_t kMagic[] = { 0xDE, 0xAD, 0xBE, 0xEF };
36
37 void* RAM_AccessIf::g_m_plock = NULL;
38 void* RAM_AccessIf::g_m_bakup_map = MAP_FAILED;
39 bool RAM_AccessIf::g_m_is_first_access = false;
40
41 typedef struct {
42   char magic_in[4];
43   RAM_SM_INFO_t data0;
44   uint32_t checksum0;
45   RAM_SM_INFO_t data1;
46   uint32_t checksum1;
47   char magic_out[4];
48 } RAM_SM_DRAM_INFO_t;
49
50 void RAM_AccessIf::initRamBackupEnable(RAM_WAKEUP_STATE wupState) {
51   RAM_SM_DRAM_INFO_t* p_buf;
52   CSMChecksum l_checksum;
53
54   ROM_ACCESS_STATIC_ASERT(sizeof(RAM_SM_DRAM_INFO_t) <= SS_SYS_AREA_RAM_MAX_SIZE);
55   // Checking sizes because checksum calculations expect 4 bytes alignments
56   ROM_ACCESS_STATIC_ASERT((sizeof(RAM_SM_DRAM_INFO_t) % sizeof(UI_32)) == 0);
57
58   if (g_m_bakup_map == MAP_FAILED) {
59     g_m_bakup_map = EL_mem_exram_mmap(  // LCOV_EXCL_BR_LINE 11:unexpected branch
60         EL_MEM_TYPE_REGION_SYS,
61         EL_mem_getOffset(EL_MEM_ID_SYS_BOOT) + SS_SYS_AREA_RAM_OFFSET,  // LCOV_EXCL_BR_LINE 11:unexpected branch
62         SS_SYS_AREA_RAM_MAX_SIZE, PROT_READ | PROT_WRITE, MAP_SHARED,
63         EL_MEM_CACHE_INVALID);
64     // LCOV_EXCL_BR_START 6:impossible to confirm because g_m_bakup_map can not be changed
65     if (g_m_bakup_map == MAP_FAILED) {
66     // LCOV_EXCL_BR_STOP
67       AGL_ASSERT_NOT_TESTED();  // LCOV_EXCL_LINE 200: test assert
68       ROM_ACCESS_ERRNO(0);  // LCOV_EXCL_LINE 6:impossible to confirm because g_m_bakup_map can not be changed
69       return;  // LCOV_EXCL_LINE 6:impossible to confirm because g_m_bakup_map can not be changed
70     }
71   }
72   p_buf = static_cast<RAM_SM_DRAM_INFO_t*>(g_m_bakup_map);
73
74   // LCOV_EXCL_BR_START 6:impossible to confirm because wupState can not be changed
75   if ((RAM_WAKEUP_STATE_BACKUP_NG == wupState) ||
76       (RAM_WAKEUP_STATE_BATTERY_DOWN == wupState) ||
77       (memcmp(p_buf->magic_out, kMagic, sizeof(kMagic)) != 0) ||
78       (memcmp(p_buf->magic_in, p_buf->magic_out, sizeof(p_buf->magic_in)) != 0)) {
79   // LCOV_EXCL_BR_STOP
80     // BACKUP NG
81     g_m_is_first_access = false;
82     bzero(p_buf, sizeof(RAM_SM_DRAM_INFO_t));
83   }
84
85   if (!g_m_is_first_access) {
86     // LCOV_EXCL_BR_START 11:unexpected branch
87     if ((memcmp(p_buf->data0.signature_in, kSigNature, sizeof(kSigNature)) == 0)
88         && (memcmp(p_buf->data0.signature_out, kSigNature,
89                    sizeof(kSigNature)) == 0)
90         && (l_checksum.cal_checksum(&(p_buf->data0), sizeof(p_buf->data0)) == p_buf->checksum0)) {
91     // LCOV_EXCL_BR_STOP
92       // Use data0 content
93       memcpy(&(p_buf->data1), &(p_buf->data0), sizeof(p_buf->data1));
94       p_buf->checksum1 = p_buf->checksum0;
95     // LCOV_EXCL_BR_START 11:unexpected branch
96     } else if ((memcmp(p_buf->data1.signature_in, kSigNature, sizeof(kSigNature)) == 0)
97         && (memcmp(p_buf->data1.signature_out, kSigNature,
98                    sizeof(kSigNature)) == 0)
99         && (l_checksum.cal_checksum(&(p_buf->data1), sizeof(p_buf->data1)) == p_buf->checksum1)) {
100     // LCOV_EXCL_BR_STOP
101       // Use data1 content
102       memcpy(&(p_buf->data0), &(p_buf->data1), sizeof(p_buf->data0));
103       p_buf->checksum0 = p_buf->checksum1;
104     } else {
105       // BACKUP NG or SIGNATURE CHECK or CHECK SUM NG
106       bzero(p_buf, sizeof(RAM_SM_DRAM_INFO_t));
107       memcpy(p_buf->magic_in, kMagic, sizeof(kMagic));
108       // data0
109       memcpy(p_buf->data0.signature_in, kSigNature, sizeof(kSigNature));
110       memcpy(p_buf->data0.signature_out, kSigNature, sizeof(kSigNature));
111       p_buf->checksum0 =
112           l_checksum.cal_checksum(&(p_buf->data0), sizeof(p_buf->data0));  // LCOV_EXCL_BR_LINE 11:unexpected branch
113       // data1
114       memcpy(p_buf->data1.signature_in, kSigNature, sizeof(kSigNature));
115       memcpy(p_buf->data1.signature_out, kSigNature, sizeof(kSigNature));
116       p_buf->checksum1 =
117           l_checksum.cal_checksum(&(p_buf->data1), sizeof(p_buf->data1));  // LCOV_EXCL_BR_LINE 11:unexpected branch
118       memcpy(p_buf->magic_out, kMagic, sizeof(kMagic));
119     }
120   }
121   memcpy(&m_buf, &(p_buf->data0), sizeof(p_buf->data0));
122 }
123
124 void RAM_AccessIf::finalRamBackupEnable(void) {
125   RAM_SM_DRAM_INFO_t* p_buf;
126   CSMChecksum l_checksum;
127   // LCOV_EXCL_BR_START 6:impossible to confirm because g_m_bakup_map can not be changed
128   if (g_m_bakup_map == MAP_FAILED) {
129   // LCOV_EXCL_BR_STOP
130     AGL_ASSERT_NOT_TESTED();  // LCOV_EXCL_LINE 200: test assert
131     ROM_ACCESS_ASERT(0);  // LCOV_EXCL_LINE 6:impossible to confirm because g_m_bakup_map can not be changed
132     return;  // LCOV_EXCL_LINE 6:impossible to confirm because g_m_bakup_map can not be changed
133   }
134
135   p_buf = static_cast<RAM_SM_DRAM_INFO_t*>(g_m_bakup_map);
136
137   // kSigNature is cleared during writing
138   bzero(m_buf.signature_in, sizeof(kSigNature));
139
140   // data0
141   memcpy(&(p_buf->data0), &m_buf, sizeof(p_buf->data0));
142   memcpy(p_buf->data0.signature_in, kSigNature, sizeof(kSigNature));
143   p_buf->checksum0 = l_checksum.cal_checksum(&(p_buf->data0),  // LCOV_EXCL_BR_LINE 11:unexpected branch
144                                              sizeof(p_buf->data0));
145
146   // data1
147   memcpy(&(p_buf->data1), &m_buf, sizeof(p_buf->data1));
148   memcpy(p_buf->data1.signature_in, kSigNature, sizeof(kSigNature));
149   p_buf->checksum1 = l_checksum.cal_checksum(&(p_buf->data1),  // LCOV_EXCL_BR_LINE 11:unexpected branch
150                                              sizeof(p_buf->data1));
151
152   // Set kSigNature
153   memcpy(m_buf.signature_in, kSigNature,
154          sizeof(kSigNature));
155 }
156
157 RAM_AccessIf::RAM_AccessIf(
158     RAM_WAKEUP_STATE wupState /*  = RAM_WAKEUP_STATE_DONT_CARE */)
159     : m_buf(),
160       m_dirty(false) {
161
162   if (g_m_plock == NULL) {  // LCOV_EXCL_BR_LINE 6:impossible to confirm because g_m_plock can not be changed
163     g_m_plock = CL_LockMap(LOCK_RAM_ACCESS_IF);
164     if (g_m_plock == MAP_FAILED) {
165       ROM_ACCESS_ASERT(0);  // LCOV_EXCL_BR_LINE 6:impossible to confirm because g_m_plock can not be changed
166       // LCOV_EXCL_BR_START 6:impossible to confirm because g_m_plock can not be changed
167       FRAMEWORKUNIFIEDLOG(
168           ZONE_ERR, __FUNCTION__,
169           "CL_LockMap Error, please check whether you call CL_LockProcessInit");
170       // LCOV_EXCL_BR_STOP
171       g_m_plock = NULL;
172     }
173   }
174   if (g_m_plock) {
175     if (0 != CL_LockGet(g_m_plock)) {
176       ROM_ACCESS_ASERT(0);
177     }
178   }
179
180   if (RAM_WAKEUP_STATE_BATTERY_DOWN == wupState) {    // LCOV_EXCL_BR_LINE 13:
181     // Models without DRAM backups are initialized when +B is down.
182     // Deletes files because models with DRAM backups are also backwards compatible
183     AGL_ASSERT_NOT_TESTED();  // LCOV_EXCL_LINE 200: test assert
184     unlink(RAM_PATH);  // LCOV_EXCL_LINE 13:
185     unlink(RAM_OLD_PATH);  // LCOV_EXCL_LINE 13:
186   }
187
188   initRamBackupEnable(wupState);
189   g_m_is_first_access = true;
190 }
191
192 RAM_AccessIf::~RAM_AccessIf() {
193   if (m_dirty) {
194     finalRamBackupEnable();
195   }
196   if (g_m_plock) {
197     ROM_ACCESS_ASERT(0 == CL_LockRelease(g_m_plock));
198   }
199
200   return;
201 }
202
203 EFrameworkunifiedStatus RAM_AccessIf::getRamInfo(RAM_SM_INFO_t* p_bootInfo) {
204   *p_bootInfo = m_buf;
205   return eFrameworkunifiedStatusOK;
206 }
207
208 EFrameworkunifiedStatus RAM_AccessIf::setRamInfo(RAM_SM_INFO_t* p_bootInfo) {
209   if (0 != memcmp(&m_buf, p_bootInfo, sizeof(m_buf))) {  // LCOV_EXCL_BR_LINE 11:unexpected branch
210     m_buf = *p_bootInfo;
211     m_dirty = true;
212   }
213
214   return eFrameworkunifiedStatusOK;
215 }