blob: 13a35f43e86befa1ea75d4133d44f883c3a95ea9 [file] [log] [blame]
tharun kumarae860532017-06-28 16:56:10 +05301Introduction
2============
3
4The goal of this debug feature is to provide a reliable, responsive,
5accurate and secure debug capability to developers interested in
6debugging MSM subsystem processor images without the use of a hardware
7debugger.
8
9The Debug Agent along with the Remote Debug Driver implements a shared
10memory based transport mechanism that allows for a debugger (ex. GDB)
11running on a host PC to communicate with a remote stub running on
12peripheral subsystems such as the ADSP, MODEM etc.
13
14The diagram below depicts end to end the components involved to
15support remote debugging:
16
17
18: :
19: HOST (PC) : MSM
20: ,--------, : ,-------,
21: | | : | Debug | ,--------,
22: |Debugger|<--:-->| Agent | | Remote |
23: | | : | App | +----->| Debug |
24: `--------` : |-------| ,--------, | | Stub |
25: : | Remote| | |<---+ `--------`
26: : | Debug |<-->|--------|
27: : | Driver| | |<---+ ,--------,
28: : `-------` `--------` | | Remote |
29: : LA Shared +----->| Debug |
30: : Memory | Stub |
31: : `--------`
32: : Peripheral Subsystems
33: : (ADSP, MODEM, ...)
34
35
36Debugger: Debugger application running on the host PC that
37 communicates with the remote stub.
38 Examples: GDB, LLDB
39
40Debug Agent: Software that runs on the Linux Android platform
41 that provides connectivity from the MSM to the
42 host PC. This involves two portions:
43 1) User mode Debug Agent application that discovers
44 processes running on the subsystems and creates
45 TCP/IP sockets for the host to connect to. In addition
46 to this, it creates an info (or meta) port that
47 users can connect to discover the various
48 processes and their corresponding debug ports.
49
50Remote Debug A character based driver that the Debug
51Driver: Agent uses to transport the payload received from the
52 host to the debug stub running on the subsystem
53 processor over shared memory and vice versa.
54
55Shared Memory: Shared memory from the SMEM pool that is accessible
56 from the Applications Processor (AP) and the
57 subsystem processors.
58
59Remote Debug Privileged code that runs in the kernels of the
60Stub: subsystem processors that receives debug commands
61 from the debugger running on the host and
62 acts on these commands. These commands include reading
63 and writing to registers and memory belonging to the
64 subsystem's address space, setting breakpoints,
65 single stepping etc.
66
67Hardware description
68====================
69
70The Remote Debug Driver interfaces with the Remote Debug stubs
71running on the subsystem processors and does not drive or
72manage any hardware resources.
73
74Software description
75====================
76
77The debugger and the remote stubs use Remote Serial Protocol (RSP)
78to communicate with each other. This is widely used protocol by both
79software and hardware debuggers. RSP is an ASCII based protocol
80and used when it is not possible to run GDB server on the target under
81debug.
82
83The Debug Agent application along with the Remote Debug Driver
84is responsible for establishing a bi-directional connection from
85the debugger application running on the host to the remote debug
86stub running on a subsystem. The Debug Agent establishes connectivity
87to the host PC via TCP/IP sockets.
88
89This feature uses ADB port forwarding to establish connectivity
90between the debugger running on the host and the target under debug.
91
92Please note the Debug Agent does not expose HLOS memory to the
93remote subsystem processors.
94
95Design
96======
97
98Here is the overall flow:
99
1001) When the Debug Agent application starts up, it opens up a shared memory
101based transport channel to the various subsystem processor images.
102
1032) The Debug Agent application sends messages across to the remote stubs
104to discover the various processes that are running on the subsystem and
105creates debug sockets for each of them.
106
1073) Whenever a process running on a subsystem exits, the Debug Agent
108is notified by the stub so that the debug port and other resources
109can be reclaimed.
110
1114) The Debug Agent uses the services of the Remote Debug Driver to
112transport payload from the host debugger to the remote stub and vice versa.
113
1145) Communication between the Remote Debug Driver and the Remote Debug stub
115running on the subsystem processor is done over shared memory (see figure).
116SMEM services are used to allocate the shared memory that will
117be readable and writeable by the AP and the subsystem image under debug.
118
119A separate SMEM allocation takes place for each subsystem processor
120involved in remote debugging. The remote stub running on each of the
121subsystems allocates a SMEM buffer using a unique identifier so that both
122the AP and subsystem get the same physical block of memory. It should be
123noted that subsystem images can be restarted at any time.
124However, when a subsystem comes back up, its stub uses the same unique
125SMEM identifier to allocate the SMEM block. This would not result in a
126new allocation rather the same block of memory in the first bootup instance
127is provided back to the stub running on the subsystem.
128
129An 8KB chunk of shared memory is allocated and used for communication
130per subsystem. For multi-process capable subsystems, 16KB chunk of shared
131memory is allocated to allow for simultaneous debugging of more than one
132process running on a single subsystem.
133
134The shared memory is used as a circular ring buffer in each direction.
135Thus we have a bi-directional shared memory channel between the AP
136and a subsystem. We call this SMQ. Each memory channel contains a header,
137data and a control mechanism that is used to synchronize read and write
138of data between the AP and the remote subsystem.
139
140Overall SMQ memory view:
141:
142: +------------------------------------------------+
143: | SMEM buffer |
144: |-----------------------+------------------------|
145: |Producer: LA | Producer: Remote |
146: |Consumer: Remote | subsystem |
147: | subsystem | Consumer: LA |
148: | | |
149: | Producer| Consumer|
150: +-----------------------+------------------------+
151: | |
152: | |
153: | +--------------------------------------+
154: | |
155: | |
156: v v
157: +--------------------------------------------------------------+
158: | Header | Data | Control |
159: +-----------+---+---+---+-----+----+--+--+-----+---+--+--+-----+
160: | | b | b | b | | S |n |n | | S |n |n | |
161: | Producer | l | l | l | | M |o |o | | M |o |o | |
162: | Ver | o | o | o | | Q |d |d | | Q |d |d | |
163: |-----------| c | c | c | ... | |e |e | ... | |e |e | ... |
164: | | k | k | k | | O | | | | I | | | |
165: | Consumer | | | | | u |0 |1 | | n |0 |1 | |
166: | Ver | 0 | 1 | 2 | | t | | | | | | | |
167: +-----------+---+---+---+-----+----+--+--+-----+---+--+--+-----+
168: | |
169: + |
170: |
171: +------------------------+
172: |
173: v
174: +----+----+----+----+
175: | SMQ Nodes |
176: |----|----|----|----|
177: Node # | 0 | 1 | 2 | ...|
178: |----|----|----|----|
179: Starting Block Index # | 0 | 3 | 8 | ...|
180: |----|----|----|----|
181: # of blocks | 3 | 5 | 1 | ...|
182: +----+----+----+----+
183:
184
185Header: Contains version numbers for software compatibility to ensure
186that both producers and consumers on the AP and subsystems know how to
187read from and write to the queue.
188Both the producer and consumer versions are 1.
189: +---------+-------------------+
190: | Size | Field |
191: +---------+-------------------+
192: | 1 byte | Producer Version |
193: +---------+-------------------+
194: | 1 byte | Consumer Version |
195: +---------+-------------------+
196
197
198Data: The data portion contains multiple blocks [0..N] of a fixed size.
199The block size SM_BLOCKSIZE is fixed to 128 bytes for header version #1.
200Payload sent from the debug agent app is split (if necessary) and placed
201in these blocks. The first data block is placed at the next 8 byte aligned
202address after the header.
203
204The number of blocks for a given SMEM allocation is derived as follows:
205 Number of Blocks = ((Total Size - Alignment - Size of Header
206 - Size of SMQIn - Size of SMQOut)/(SM_BLOCKSIZE))
207
208The producer maintains a private block map of each of these blocks to
209determine which of these blocks in the queue is available and which are free.
210
211Control:
212The control portion contains a list of nodes [0..N] where N is number
213of available data blocks. Each node identifies the data
214block indexes that contain a particular debug message to be transferred,
215and the number of blocks it took to hold the contents of the message.
216
217Each node has the following structure:
218: +---------+-------------------+
219: | Size | Field |
220: +---------+-------------------+
221: | 2 bytes |Staring Block Index|
222: +---------+-------------------+
223: | 2 bytes |Number of Blocks |
224: +---------+-------------------+
225
226The producer and the consumer update different parts of the control channel
227(SMQOut / SMQIn) respectively. Each of these control data structures contains
228information about the last node that was written / read, and the actual nodes
229that were written/read.
230
231SMQOut Structure (R/W by producer, R by consumer):
232: +---------+-------------------+
233: | Size | Field |
234: +---------+-------------------+
235: | 4 bytes | Magic Init Number |
236: +---------+-------------------+
237: | 4 bytes | Reset |
238: +---------+-------------------+
239: | 4 bytes | Last Sent Index |
240: +---------+-------------------+
241: | 4 bytes | Index Free Read |
242: +---------+-------------------+
243
244SMQIn Structure (R/W by consumer, R by producer):
245: +---------+-------------------+
246: | Size | Field |
247: +---------+-------------------+
248: | 4 bytes | Magic Init Number |
249: +---------+-------------------+
250: | 4 bytes | Reset ACK |
251: +---------+-------------------+
252: | 4 bytes | Last Read Index |
253: +---------+-------------------+
254: | 4 bytes | Index Free Write |
255: +---------+-------------------+
256
257Magic Init Number:
258Both SMQ Out and SMQ In initialize this field with a predefined magic
259number so as to make sure that both the consumer and producer blocks
260have fully initialized and have valid data in the shared memory control area.
261 Producer Magic #: 0xFF00FF01
262 Consumer Magic #: 0xFF00FF02
263
264SMQ Out's Last Sent Index and Index Free Read:
265 Only a producer can write to these indexes and they are updated whenever
266 there is new payload to be inserted into the SMQ in order to be sent to a
267 consumer.
268
269 The number of blocks required for the SMQ allocation is determined as:
270 (payload size + SM_BLOCKSIZE - 1) / SM_BLOCKSIZE
271
272 The private block map is searched for a large enough continuous set of blocks
273 and the user data is copied into the data blocks.
274
275 The starting index of the free block(s) is updated in the SMQOut's Last Sent
276 Index. This update keeps track of which index was last written to and the
277 producer uses it to determine where the the next allocation could be done.
278
279 Every allocation, a producer updates the Index Free Read from its
280 collaborating consumer's Index Free Write field (if they are unequal).
281 This index value indicates that the consumer has read all blocks associated
282 with allocation on the SMQ and that the producer can reuse these blocks for
283 subsquent allocations since this is a circular queue.
284
285 At cold boot and restart, these indexes are initialized to zero and all
286 blocks are marked as available for allocation.
287
288SMQ In's Last Read Index and Index Free Write:
289 These indexes are written to only by a consumer and are updated whenever
290 there is new payload to be read from the SMQ. The Last Read Index keeps
291 track of which index was last read by the consumer and using this, it
292 determines where the next read should be done.
293 After completing a read, Last Read Index is incremented to the
294 next block index. A consumer updates Index Free Write to the starting
295 index of an allocation whenever it has completed processing the blocks.
296 This is an optimization that can be used to prevent an additional copy
297 of data from the queue into a client's data buffer and the data in the queue
298 itself can be used.
299 Once Index Free Write is updated, the collaborating producer (on the next
300 data allocation) reads the updated Index Free Write value and it then
301 updates its corresponding SMQ Out's Index Free Read and marks the blocks
302 associated with that index as available for allocation. At cold boot and
303 restart, these indexes are initialized to zero.
304
305SMQ Out Reset# and SMQ In Reset ACK #:
306 Since subsystems can restart at anytime, the data blocks and control channel
307 can be in an inconsistent state when a producer or consumer comes up.
308 We use Reset and Reset ACK to manage this. At cold boot, the producer
309 initializes the Reset# to a known number ex. 1. Every other reset that the
310 producer undergoes, the Reset#1 is simply incremented by 1. All the producer
311 indexes are reset.
312 When the producer notifies the consumer of data availability, the consumer
313 reads the producers Reset # and copies that into its SMQ In Reset ACK#
314 field when they differ. When that occurs, the consumer resets its
315 indexes to 0.
316
3176) Asynchronous notifications between a producer and consumer are
318done using the SMP2P service which is interrupt based.
319
320Power Management
321================
322
323None
324
325SMP/multi-core
326==============
327
328The driver uses completion to wake up the Debug Agent client threads.
329
330Security
331========
332
333From the perspective of the subsystem, the AP is untrusted. The remote
334stubs consult the secure debug fuses to determine whether or not the
335remote debugging will be enabled at the subsystem.
336
337If the hardware debug fuses indicate that debugging is disabled, the
338remote stubs will not be functional on the subsystem. Writes to the
339queue will only be done if the driver sees that the remote stub has been
340initialized on the subsystem.
341
342Therefore even if any untrusted software running on the AP requests
343the services of the Remote Debug Driver and inject RSP messages
344into the shared memory buffer, these RSP messages will be discarded and
345an appropriate error code will be sent up to the invoking application.
346
347Performance
348===========
349
350During operation, the Remote Debug Driver copies RSP messages
351asynchronously sent from the host debugger to the remote stub and vice
352versa. The debug messages are ASCII based and relatively short
353(<25 bytes) and may once in a while go up to a maximum 700 bytes
354depending on the command the user requested. Thus we do not
355anticipate any major performance impact. Moreover, in a typical
356functional debug scenario performance should not be a concern.
357
358Interface
359=========
360
361The Remote Debug Driver is a character based device that manages
362a piece of shared memory that is used as a bi-directional
363single producer/consumer circular queue using a next fit allocator.
364Every subsystem, has its own shared memory buffer that is managed
365like a separate device.
366
367The driver distinguishes each subsystem processor's buffer by
368registering a node with a different minor number.
369
370For each subsystem that is supported, the driver exposes a user space
371interface through the following node:
372 - /dev/rdbg-<subsystem>
373 Ex. /dev/rdbg-adsp (for the ADSP subsystem)
374
375The standard open(), close(), read() and write() API set is
376implemented.
377
378The open() syscall will fail if a subsystem is not present or supported
379by the driver or a shared memory buffer cannot be allocated for the
380AP - subsystem communication. It will also fail if the subsytem has
381not initialized the queue on its side. Here are the error codes returned
382in case a call to open() fails:
383ENODEV - memory was not yet allocated for the device
384EEXIST - device is already opened
385ENOMEM - SMEM allocation failed
386ECOMM - Subsytem queue is not yet setup
387ENOMEM - Failure to initialize SMQ
388
389read() is a blocking call that will return with the number of bytes written
390by the subsystem whenever the subsystem sends it some payload. Here are the
391error codes returned in case a call to read() fails:
392EINVAL - Invalid input
393ENODEV - Device has not been opened yet
394ERESTARTSYS - call to wait_for_completion_interruptible is interrupted
395ENODATA - call to smq_receive failed
396
397write() attempts to send user mode payload out to the subsystem. It can fail
398if the SMQ is full. The number of bytes written is returned back to the user.
399Here are the error codes returned in case a call to write() fails:
400EINVAL - Invalid input
401ECOMM - SMQ send failed
402
403In the close() syscall, the control information state of the SMQ is
404initialized to zero thereby preventing any further communication between
405the AP and the subsystem. Here is the error code returned in case
406a call to close() fails:
407ENODEV - device wasn't opened/initialized
408
409The Remote Debug driver uses SMP2P for bi-directional AP to subsystem
410notification. Notifications are sent to indicate that there are new
411debug messages available for processing. Each subsystem that is
412supported will need to add a device tree entry per the usage
413specification of SMP2P driver.
414
415In case the remote stub becomes non operational or the security configuration
416on the subsystem does not permit debugging, any messages put in the SMQ will
417not be responded to. It is the responsibility of the Debug Agent app and the
418host debugger application such as GDB to timeout and notify the user of the
419non availability of remote debugging.
420
421Driver parameters
422=================
423
424None
425
426Config options
427==============
428
429The driver is configured with a device tree entry to map an SMP2P entry
430to the device. The SMP2P entry name used is "rdbg". Please see
431kernel\Documentation\arm\msm\msm_smp2p.txt for information about the
432device tree entry required to configure SMP2P.
433
434The driver uses the SMEM allocation type SMEM_LC_DEBUGGER to allocate memory
435for the queue that is used to share data with the subsystems.
436
437Dependencies
438============
439
440The Debug Agent driver requires services of SMEM to
441allocate shared memory buffers.
442
443SMP2P is used as a bi-directional notification
444mechanism between the AP and a subsystem processor.
445
446User space utilities
447====================
448
449This driver is meant to be used in conjunction with the user mode
450Remote Debug Agent application.
451
452Other
453=====
454
455None
456
457Known issues
458============
459For targets with an external subsystem, we cannot use
460shared memory for communication and would have to use the prevailing
461transport mechanisms that exists between the AP and the external subsystem.
462
463This driver cannot be leveraged for such targets.
464
465To do
466=====
467
468None