1 // Copyright 2020 The Pigweed Authors 2 // 3 // Licensed under the Apache License, Version 2.0 (the "License"); you may not 4 // use this file except in compliance with the License. You may obtain a copy of 5 // the License at 6 // 7 // https://www.apache.org/licenses/LICENSE-2.0 8 // 9 // Unless required by applicable law or agreed to in writing, software 10 // distributed under the License is distributed on an "AS IS" BASIS, WITHOUT 11 // WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the 12 // License for the specific language governing permissions and limitations under 13 // the License. 14 #include "pw_cpu_exception_cortex_m/cpu_state.h" 15 #include "pw_cpu_exception_cortex_m_protos/cpu_state.pwpb.h" 16 #include "pw_preprocessor/compiler.h" 17 #include "pw_protobuf/encoder.h" 18 19 namespace pw::cpu_exception { 20 DumpCpuStateProto(protobuf::Encoder & dest,const pw_cpu_exception_State & cpu_state)21Status DumpCpuStateProto(protobuf::Encoder& dest, 22 const pw_cpu_exception_State& cpu_state) { 23 cortex_m::ArmV7mCpuState::Encoder state_encoder(&dest); 24 25 // Special and mem-mapped registers. 26 state_encoder.WritePc(cpu_state.base.pc); 27 state_encoder.WriteLr(cpu_state.base.lr); 28 state_encoder.WritePsr(cpu_state.base.psr); 29 state_encoder.WriteMsp(cpu_state.extended.msp); 30 state_encoder.WritePsp(cpu_state.extended.psp); 31 state_encoder.WriteExcReturn(cpu_state.extended.exc_return); 32 state_encoder.WriteCfsr(cpu_state.extended.cfsr); 33 state_encoder.WriteMmfar(cpu_state.extended.mmfar); 34 state_encoder.WriteBfar(cpu_state.extended.bfar); 35 state_encoder.WriteIcsr(cpu_state.extended.icsr); 36 state_encoder.WriteHfsr(cpu_state.extended.hfsr); 37 state_encoder.WriteShcsr(cpu_state.extended.shcsr); 38 state_encoder.WriteControl(cpu_state.extended.control); 39 40 // General purpose registers. 41 state_encoder.WriteR0(cpu_state.base.r0); 42 state_encoder.WriteR1(cpu_state.base.r1); 43 state_encoder.WriteR2(cpu_state.base.r2); 44 state_encoder.WriteR3(cpu_state.base.r3); 45 state_encoder.WriteR4(cpu_state.extended.r4); 46 state_encoder.WriteR5(cpu_state.extended.r5); 47 state_encoder.WriteR6(cpu_state.extended.r6); 48 state_encoder.WriteR7(cpu_state.extended.r7); 49 state_encoder.WriteR8(cpu_state.extended.r8); 50 state_encoder.WriteR9(cpu_state.extended.r9); 51 state_encoder.WriteR10(cpu_state.extended.r10); 52 state_encoder.WriteR11(cpu_state.extended.r11); 53 54 // If the encode buffer was exhausted in an earlier write, it will be 55 // reflected here. 56 Status status = state_encoder.WriteR12(cpu_state.base.r12); 57 if (!status.ok()) { 58 return status.IsResourceExhausted() ? Status::ResourceExhausted() 59 : Status::Unknown(); 60 } 61 return OkStatus(); 62 } 63 64 } // namespace pw::cpu_exception 65