174fe6c29SRuslan Bukin /*
2*85f87cf4SRuslan Bukin * Copyright (c) 2014-2019, Intel Corporation
374fe6c29SRuslan Bukin *
474fe6c29SRuslan Bukin * Redistribution and use in source and binary forms, with or without
574fe6c29SRuslan Bukin * modification, are permitted provided that the following conditions are met:
674fe6c29SRuslan Bukin *
774fe6c29SRuslan Bukin * * Redistributions of source code must retain the above copyright notice,
874fe6c29SRuslan Bukin * this list of conditions and the following disclaimer.
974fe6c29SRuslan Bukin * * Redistributions in binary form must reproduce the above copyright notice,
1074fe6c29SRuslan Bukin * this list of conditions and the following disclaimer in the documentation
1174fe6c29SRuslan Bukin * and/or other materials provided with the distribution.
1274fe6c29SRuslan Bukin * * Neither the name of Intel Corporation nor the names of its contributors
1374fe6c29SRuslan Bukin * may be used to endorse or promote products derived from this software
1474fe6c29SRuslan Bukin * without specific prior written permission.
1574fe6c29SRuslan Bukin *
1674fe6c29SRuslan Bukin * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
1774fe6c29SRuslan Bukin * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
1874fe6c29SRuslan Bukin * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
1974fe6c29SRuslan Bukin * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
2074fe6c29SRuslan Bukin * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
2174fe6c29SRuslan Bukin * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
2274fe6c29SRuslan Bukin * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
2374fe6c29SRuslan Bukin * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
2474fe6c29SRuslan Bukin * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
2574fe6c29SRuslan Bukin * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
2674fe6c29SRuslan Bukin * POSSIBILITY OF SUCH DAMAGE.
2774fe6c29SRuslan Bukin */
2874fe6c29SRuslan Bukin
2974fe6c29SRuslan Bukin #include "pt_packet_decoder.h"
3074fe6c29SRuslan Bukin #include "pt_decoder_function.h"
3174fe6c29SRuslan Bukin #include "pt_packet.h"
3274fe6c29SRuslan Bukin #include "pt_sync.h"
3374fe6c29SRuslan Bukin #include "pt_config.h"
3474fe6c29SRuslan Bukin #include "pt_opcodes.h"
3574fe6c29SRuslan Bukin
3674fe6c29SRuslan Bukin #include <string.h>
3774fe6c29SRuslan Bukin #include <stdlib.h>
38*85f87cf4SRuslan Bukin #include <stddef.h>
3974fe6c29SRuslan Bukin
4074fe6c29SRuslan Bukin
pt_pkt_decoder_init(struct pt_packet_decoder * decoder,const struct pt_config * config)4174fe6c29SRuslan Bukin int pt_pkt_decoder_init(struct pt_packet_decoder *decoder,
4274fe6c29SRuslan Bukin const struct pt_config *config)
4374fe6c29SRuslan Bukin {
4474fe6c29SRuslan Bukin int errcode;
4574fe6c29SRuslan Bukin
4674fe6c29SRuslan Bukin if (!decoder || !config)
4774fe6c29SRuslan Bukin return -pte_invalid;
4874fe6c29SRuslan Bukin
4974fe6c29SRuslan Bukin memset(decoder, 0, sizeof(*decoder));
5074fe6c29SRuslan Bukin
5174fe6c29SRuslan Bukin errcode = pt_config_from_user(&decoder->config, config);
5274fe6c29SRuslan Bukin if (errcode < 0)
5374fe6c29SRuslan Bukin return errcode;
5474fe6c29SRuslan Bukin
5574fe6c29SRuslan Bukin return 0;
5674fe6c29SRuslan Bukin }
5774fe6c29SRuslan Bukin
pt_pkt_alloc_decoder(const struct pt_config * config)5874fe6c29SRuslan Bukin struct pt_packet_decoder *pt_pkt_alloc_decoder(const struct pt_config *config)
5974fe6c29SRuslan Bukin {
6074fe6c29SRuslan Bukin struct pt_packet_decoder *decoder;
6174fe6c29SRuslan Bukin int errcode;
6274fe6c29SRuslan Bukin
6374fe6c29SRuslan Bukin decoder = malloc(sizeof(*decoder));
6474fe6c29SRuslan Bukin if (!decoder)
6574fe6c29SRuslan Bukin return NULL;
6674fe6c29SRuslan Bukin
6774fe6c29SRuslan Bukin errcode = pt_pkt_decoder_init(decoder, config);
6874fe6c29SRuslan Bukin if (errcode < 0) {
6974fe6c29SRuslan Bukin free(decoder);
7074fe6c29SRuslan Bukin return NULL;
7174fe6c29SRuslan Bukin }
7274fe6c29SRuslan Bukin
7374fe6c29SRuslan Bukin return decoder;
7474fe6c29SRuslan Bukin }
7574fe6c29SRuslan Bukin
pt_pkt_decoder_fini(struct pt_packet_decoder * decoder)7674fe6c29SRuslan Bukin void pt_pkt_decoder_fini(struct pt_packet_decoder *decoder)
7774fe6c29SRuslan Bukin {
7874fe6c29SRuslan Bukin (void) decoder;
7974fe6c29SRuslan Bukin
8074fe6c29SRuslan Bukin /* Nothing to do. */
8174fe6c29SRuslan Bukin }
8274fe6c29SRuslan Bukin
pt_pkt_free_decoder(struct pt_packet_decoder * decoder)8374fe6c29SRuslan Bukin void pt_pkt_free_decoder(struct pt_packet_decoder *decoder)
8474fe6c29SRuslan Bukin {
8574fe6c29SRuslan Bukin pt_pkt_decoder_fini(decoder);
8674fe6c29SRuslan Bukin free(decoder);
8774fe6c29SRuslan Bukin }
8874fe6c29SRuslan Bukin
pt_pkt_sync_forward(struct pt_packet_decoder * decoder)8974fe6c29SRuslan Bukin int pt_pkt_sync_forward(struct pt_packet_decoder *decoder)
9074fe6c29SRuslan Bukin {
91*85f87cf4SRuslan Bukin const uint8_t *pos, *sync, *begin;
92*85f87cf4SRuslan Bukin ptrdiff_t space;
9374fe6c29SRuslan Bukin int errcode;
9474fe6c29SRuslan Bukin
9574fe6c29SRuslan Bukin if (!decoder)
9674fe6c29SRuslan Bukin return -pte_invalid;
9774fe6c29SRuslan Bukin
98*85f87cf4SRuslan Bukin begin = decoder->config.begin;
9974fe6c29SRuslan Bukin sync = decoder->sync;
10074fe6c29SRuslan Bukin pos = decoder->pos;
10174fe6c29SRuslan Bukin if (!pos)
102*85f87cf4SRuslan Bukin pos = begin;
10374fe6c29SRuslan Bukin
10474fe6c29SRuslan Bukin if (pos == sync)
10574fe6c29SRuslan Bukin pos += ptps_psb;
10674fe6c29SRuslan Bukin
107*85f87cf4SRuslan Bukin if (pos < begin)
108*85f87cf4SRuslan Bukin return -pte_internal;
109*85f87cf4SRuslan Bukin
110*85f87cf4SRuslan Bukin /* Start a bit earlier so we find PSB that have been partially consumed
111*85f87cf4SRuslan Bukin * by a preceding packet.
112*85f87cf4SRuslan Bukin */
113*85f87cf4SRuslan Bukin space = pos - begin;
114*85f87cf4SRuslan Bukin if (ptps_psb <= space)
115*85f87cf4SRuslan Bukin space = ptps_psb - 1;
116*85f87cf4SRuslan Bukin
117*85f87cf4SRuslan Bukin pos -= space;
118*85f87cf4SRuslan Bukin
11974fe6c29SRuslan Bukin errcode = pt_sync_forward(&sync, pos, &decoder->config);
12074fe6c29SRuslan Bukin if (errcode < 0)
12174fe6c29SRuslan Bukin return errcode;
12274fe6c29SRuslan Bukin
12374fe6c29SRuslan Bukin decoder->sync = sync;
12474fe6c29SRuslan Bukin decoder->pos = sync;
12574fe6c29SRuslan Bukin
12674fe6c29SRuslan Bukin return 0;
12774fe6c29SRuslan Bukin }
12874fe6c29SRuslan Bukin
pt_pkt_sync_backward(struct pt_packet_decoder * decoder)12974fe6c29SRuslan Bukin int pt_pkt_sync_backward(struct pt_packet_decoder *decoder)
13074fe6c29SRuslan Bukin {
13174fe6c29SRuslan Bukin const uint8_t *pos, *sync;
13274fe6c29SRuslan Bukin int errcode;
13374fe6c29SRuslan Bukin
13474fe6c29SRuslan Bukin if (!decoder)
13574fe6c29SRuslan Bukin return -pte_invalid;
13674fe6c29SRuslan Bukin
13774fe6c29SRuslan Bukin pos = decoder->pos;
13874fe6c29SRuslan Bukin if (!pos)
13974fe6c29SRuslan Bukin pos = decoder->config.end;
14074fe6c29SRuslan Bukin
14174fe6c29SRuslan Bukin errcode = pt_sync_backward(&sync, pos, &decoder->config);
14274fe6c29SRuslan Bukin if (errcode < 0)
14374fe6c29SRuslan Bukin return errcode;
14474fe6c29SRuslan Bukin
14574fe6c29SRuslan Bukin decoder->sync = sync;
14674fe6c29SRuslan Bukin decoder->pos = sync;
14774fe6c29SRuslan Bukin
14874fe6c29SRuslan Bukin return 0;
14974fe6c29SRuslan Bukin }
15074fe6c29SRuslan Bukin
pt_pkt_sync_set(struct pt_packet_decoder * decoder,uint64_t offset)15174fe6c29SRuslan Bukin int pt_pkt_sync_set(struct pt_packet_decoder *decoder, uint64_t offset)
15274fe6c29SRuslan Bukin {
15374fe6c29SRuslan Bukin const uint8_t *begin, *end, *pos;
15474fe6c29SRuslan Bukin
15574fe6c29SRuslan Bukin if (!decoder)
15674fe6c29SRuslan Bukin return -pte_invalid;
15774fe6c29SRuslan Bukin
15874fe6c29SRuslan Bukin begin = decoder->config.begin;
15974fe6c29SRuslan Bukin end = decoder->config.end;
16074fe6c29SRuslan Bukin pos = begin + offset;
16174fe6c29SRuslan Bukin
16274fe6c29SRuslan Bukin if (end < pos || pos < begin)
16374fe6c29SRuslan Bukin return -pte_eos;
16474fe6c29SRuslan Bukin
16574fe6c29SRuslan Bukin decoder->sync = pos;
16674fe6c29SRuslan Bukin decoder->pos = pos;
16774fe6c29SRuslan Bukin
16874fe6c29SRuslan Bukin return 0;
16974fe6c29SRuslan Bukin }
17074fe6c29SRuslan Bukin
pt_pkt_get_offset(const struct pt_packet_decoder * decoder,uint64_t * offset)17174fe6c29SRuslan Bukin int pt_pkt_get_offset(const struct pt_packet_decoder *decoder, uint64_t *offset)
17274fe6c29SRuslan Bukin {
17374fe6c29SRuslan Bukin const uint8_t *begin, *pos;
17474fe6c29SRuslan Bukin
17574fe6c29SRuslan Bukin if (!decoder || !offset)
17674fe6c29SRuslan Bukin return -pte_invalid;
17774fe6c29SRuslan Bukin
17874fe6c29SRuslan Bukin begin = decoder->config.begin;
17974fe6c29SRuslan Bukin pos = decoder->pos;
18074fe6c29SRuslan Bukin
18174fe6c29SRuslan Bukin if (!pos)
18274fe6c29SRuslan Bukin return -pte_nosync;
18374fe6c29SRuslan Bukin
184*85f87cf4SRuslan Bukin *offset = (uint64_t) (int64_t) (pos - begin);
18574fe6c29SRuslan Bukin return 0;
18674fe6c29SRuslan Bukin }
18774fe6c29SRuslan Bukin
pt_pkt_get_sync_offset(const struct pt_packet_decoder * decoder,uint64_t * offset)18874fe6c29SRuslan Bukin int pt_pkt_get_sync_offset(const struct pt_packet_decoder *decoder,
18974fe6c29SRuslan Bukin uint64_t *offset)
19074fe6c29SRuslan Bukin {
19174fe6c29SRuslan Bukin const uint8_t *begin, *sync;
19274fe6c29SRuslan Bukin
19374fe6c29SRuslan Bukin if (!decoder || !offset)
19474fe6c29SRuslan Bukin return -pte_invalid;
19574fe6c29SRuslan Bukin
19674fe6c29SRuslan Bukin begin = decoder->config.begin;
19774fe6c29SRuslan Bukin sync = decoder->sync;
19874fe6c29SRuslan Bukin
19974fe6c29SRuslan Bukin if (!sync)
20074fe6c29SRuslan Bukin return -pte_nosync;
20174fe6c29SRuslan Bukin
202*85f87cf4SRuslan Bukin *offset = (uint64_t) (int64_t) (sync - begin);
20374fe6c29SRuslan Bukin return 0;
20474fe6c29SRuslan Bukin }
20574fe6c29SRuslan Bukin
20674fe6c29SRuslan Bukin const struct pt_config *
pt_pkt_get_config(const struct pt_packet_decoder * decoder)20774fe6c29SRuslan Bukin pt_pkt_get_config(const struct pt_packet_decoder *decoder)
20874fe6c29SRuslan Bukin {
20974fe6c29SRuslan Bukin if (!decoder)
21074fe6c29SRuslan Bukin return NULL;
21174fe6c29SRuslan Bukin
21274fe6c29SRuslan Bukin return &decoder->config;
21374fe6c29SRuslan Bukin }
21474fe6c29SRuslan Bukin
pkt_to_user(struct pt_packet * upkt,size_t size,const struct pt_packet * pkt)21574fe6c29SRuslan Bukin static inline int pkt_to_user(struct pt_packet *upkt, size_t size,
21674fe6c29SRuslan Bukin const struct pt_packet *pkt)
21774fe6c29SRuslan Bukin {
21874fe6c29SRuslan Bukin if (!upkt || !pkt)
21974fe6c29SRuslan Bukin return -pte_internal;
22074fe6c29SRuslan Bukin
22174fe6c29SRuslan Bukin if (upkt == pkt)
22274fe6c29SRuslan Bukin return 0;
22374fe6c29SRuslan Bukin
22474fe6c29SRuslan Bukin /* Zero out any unknown bytes. */
22574fe6c29SRuslan Bukin if (sizeof(*pkt) < size) {
22674fe6c29SRuslan Bukin memset(upkt + sizeof(*pkt), 0, size - sizeof(*pkt));
22774fe6c29SRuslan Bukin
22874fe6c29SRuslan Bukin size = sizeof(*pkt);
22974fe6c29SRuslan Bukin }
23074fe6c29SRuslan Bukin
23174fe6c29SRuslan Bukin memcpy(upkt, pkt, size);
23274fe6c29SRuslan Bukin
23374fe6c29SRuslan Bukin return 0;
23474fe6c29SRuslan Bukin }
23574fe6c29SRuslan Bukin
pt_pkt_next(struct pt_packet_decoder * decoder,struct pt_packet * packet,size_t psize)23674fe6c29SRuslan Bukin int pt_pkt_next(struct pt_packet_decoder *decoder, struct pt_packet *packet,
23774fe6c29SRuslan Bukin size_t psize)
23874fe6c29SRuslan Bukin {
23974fe6c29SRuslan Bukin const struct pt_decoder_function *dfun;
24074fe6c29SRuslan Bukin struct pt_packet pkt, *ppkt;
24174fe6c29SRuslan Bukin int errcode, size;
24274fe6c29SRuslan Bukin
24374fe6c29SRuslan Bukin if (!packet || !decoder)
24474fe6c29SRuslan Bukin return -pte_invalid;
24574fe6c29SRuslan Bukin
24674fe6c29SRuslan Bukin ppkt = psize == sizeof(pkt) ? packet : &pkt;
24774fe6c29SRuslan Bukin
24874fe6c29SRuslan Bukin errcode = pt_df_fetch(&dfun, decoder->pos, &decoder->config);
24974fe6c29SRuslan Bukin if (errcode < 0)
25074fe6c29SRuslan Bukin return errcode;
25174fe6c29SRuslan Bukin
25274fe6c29SRuslan Bukin if (!dfun)
25374fe6c29SRuslan Bukin return -pte_internal;
25474fe6c29SRuslan Bukin
25574fe6c29SRuslan Bukin if (!dfun->packet)
25674fe6c29SRuslan Bukin return -pte_internal;
25774fe6c29SRuslan Bukin
25874fe6c29SRuslan Bukin size = dfun->packet(decoder, ppkt);
25974fe6c29SRuslan Bukin if (size < 0)
26074fe6c29SRuslan Bukin return size;
26174fe6c29SRuslan Bukin
26274fe6c29SRuslan Bukin errcode = pkt_to_user(packet, psize, ppkt);
26374fe6c29SRuslan Bukin if (errcode < 0)
26474fe6c29SRuslan Bukin return errcode;
26574fe6c29SRuslan Bukin
26674fe6c29SRuslan Bukin decoder->pos += size;
26774fe6c29SRuslan Bukin
26874fe6c29SRuslan Bukin return size;
26974fe6c29SRuslan Bukin }
27074fe6c29SRuslan Bukin
pt_pkt_decode_unknown(struct pt_packet_decoder * decoder,struct pt_packet * packet)27174fe6c29SRuslan Bukin int pt_pkt_decode_unknown(struct pt_packet_decoder *decoder,
27274fe6c29SRuslan Bukin struct pt_packet *packet)
27374fe6c29SRuslan Bukin {
27474fe6c29SRuslan Bukin int size;
27574fe6c29SRuslan Bukin
27674fe6c29SRuslan Bukin if (!decoder)
27774fe6c29SRuslan Bukin return -pte_internal;
27874fe6c29SRuslan Bukin
27974fe6c29SRuslan Bukin size = pt_pkt_read_unknown(packet, decoder->pos, &decoder->config);
28074fe6c29SRuslan Bukin if (size < 0)
28174fe6c29SRuslan Bukin return size;
28274fe6c29SRuslan Bukin
28374fe6c29SRuslan Bukin return size;
28474fe6c29SRuslan Bukin }
28574fe6c29SRuslan Bukin
pt_pkt_decode_pad(struct pt_packet_decoder * decoder,struct pt_packet * packet)28674fe6c29SRuslan Bukin int pt_pkt_decode_pad(struct pt_packet_decoder *decoder,
28774fe6c29SRuslan Bukin struct pt_packet *packet)
28874fe6c29SRuslan Bukin {
28974fe6c29SRuslan Bukin (void) decoder;
29074fe6c29SRuslan Bukin
29174fe6c29SRuslan Bukin if (!packet)
29274fe6c29SRuslan Bukin return -pte_internal;
29374fe6c29SRuslan Bukin
29474fe6c29SRuslan Bukin packet->type = ppt_pad;
29574fe6c29SRuslan Bukin packet->size = ptps_pad;
29674fe6c29SRuslan Bukin
29774fe6c29SRuslan Bukin return ptps_pad;
29874fe6c29SRuslan Bukin }
29974fe6c29SRuslan Bukin
pt_pkt_decode_psb(struct pt_packet_decoder * decoder,struct pt_packet * packet)30074fe6c29SRuslan Bukin int pt_pkt_decode_psb(struct pt_packet_decoder *decoder,
30174fe6c29SRuslan Bukin struct pt_packet *packet)
30274fe6c29SRuslan Bukin {
30374fe6c29SRuslan Bukin int size;
30474fe6c29SRuslan Bukin
30574fe6c29SRuslan Bukin if (!decoder)
30674fe6c29SRuslan Bukin return -pte_internal;
30774fe6c29SRuslan Bukin
30874fe6c29SRuslan Bukin size = pt_pkt_read_psb(decoder->pos, &decoder->config);
30974fe6c29SRuslan Bukin if (size < 0)
31074fe6c29SRuslan Bukin return size;
31174fe6c29SRuslan Bukin
31274fe6c29SRuslan Bukin packet->type = ppt_psb;
31374fe6c29SRuslan Bukin packet->size = (uint8_t) size;
31474fe6c29SRuslan Bukin
31574fe6c29SRuslan Bukin return size;
31674fe6c29SRuslan Bukin }
31774fe6c29SRuslan Bukin
pt_pkt_decode_tip(struct pt_packet_decoder * decoder,struct pt_packet * packet)31874fe6c29SRuslan Bukin int pt_pkt_decode_tip(struct pt_packet_decoder *decoder,
31974fe6c29SRuslan Bukin struct pt_packet *packet)
32074fe6c29SRuslan Bukin {
32174fe6c29SRuslan Bukin int size;
32274fe6c29SRuslan Bukin
32374fe6c29SRuslan Bukin if (!decoder || !packet)
32474fe6c29SRuslan Bukin return -pte_internal;
32574fe6c29SRuslan Bukin
32674fe6c29SRuslan Bukin size = pt_pkt_read_ip(&packet->payload.ip, decoder->pos,
32774fe6c29SRuslan Bukin &decoder->config);
32874fe6c29SRuslan Bukin if (size < 0)
32974fe6c29SRuslan Bukin return size;
33074fe6c29SRuslan Bukin
33174fe6c29SRuslan Bukin packet->type = ppt_tip;
33274fe6c29SRuslan Bukin packet->size = (uint8_t) size;
33374fe6c29SRuslan Bukin
33474fe6c29SRuslan Bukin return size;
33574fe6c29SRuslan Bukin }
33674fe6c29SRuslan Bukin
pt_pkt_decode_tnt_8(struct pt_packet_decoder * decoder,struct pt_packet * packet)33774fe6c29SRuslan Bukin int pt_pkt_decode_tnt_8(struct pt_packet_decoder *decoder,
33874fe6c29SRuslan Bukin struct pt_packet *packet)
33974fe6c29SRuslan Bukin {
34074fe6c29SRuslan Bukin int size;
34174fe6c29SRuslan Bukin
34274fe6c29SRuslan Bukin if (!decoder || !packet)
34374fe6c29SRuslan Bukin return -pte_internal;
34474fe6c29SRuslan Bukin
34574fe6c29SRuslan Bukin size = pt_pkt_read_tnt_8(&packet->payload.tnt, decoder->pos,
34674fe6c29SRuslan Bukin &decoder->config);
34774fe6c29SRuslan Bukin if (size < 0)
34874fe6c29SRuslan Bukin return size;
34974fe6c29SRuslan Bukin
35074fe6c29SRuslan Bukin packet->type = ppt_tnt_8;
35174fe6c29SRuslan Bukin packet->size = (uint8_t) size;
35274fe6c29SRuslan Bukin
35374fe6c29SRuslan Bukin return size;
35474fe6c29SRuslan Bukin }
35574fe6c29SRuslan Bukin
pt_pkt_decode_tnt_64(struct pt_packet_decoder * decoder,struct pt_packet * packet)35674fe6c29SRuslan Bukin int pt_pkt_decode_tnt_64(struct pt_packet_decoder *decoder,
35774fe6c29SRuslan Bukin struct pt_packet *packet)
35874fe6c29SRuslan Bukin {
35974fe6c29SRuslan Bukin int size;
36074fe6c29SRuslan Bukin
36174fe6c29SRuslan Bukin if (!decoder || !packet)
36274fe6c29SRuslan Bukin return -pte_internal;
36374fe6c29SRuslan Bukin
36474fe6c29SRuslan Bukin size = pt_pkt_read_tnt_64(&packet->payload.tnt, decoder->pos,
36574fe6c29SRuslan Bukin &decoder->config);
36674fe6c29SRuslan Bukin if (size < 0)
36774fe6c29SRuslan Bukin return size;
36874fe6c29SRuslan Bukin
36974fe6c29SRuslan Bukin packet->type = ppt_tnt_64;
37074fe6c29SRuslan Bukin packet->size = (uint8_t) size;
37174fe6c29SRuslan Bukin
37274fe6c29SRuslan Bukin return size;
37374fe6c29SRuslan Bukin }
37474fe6c29SRuslan Bukin
pt_pkt_decode_tip_pge(struct pt_packet_decoder * decoder,struct pt_packet * packet)37574fe6c29SRuslan Bukin int pt_pkt_decode_tip_pge(struct pt_packet_decoder *decoder,
37674fe6c29SRuslan Bukin struct pt_packet *packet)
37774fe6c29SRuslan Bukin {
37874fe6c29SRuslan Bukin int size;
37974fe6c29SRuslan Bukin
38074fe6c29SRuslan Bukin if (!decoder || !packet)
38174fe6c29SRuslan Bukin return -pte_internal;
38274fe6c29SRuslan Bukin
38374fe6c29SRuslan Bukin size = pt_pkt_read_ip(&packet->payload.ip, decoder->pos,
38474fe6c29SRuslan Bukin &decoder->config);
38574fe6c29SRuslan Bukin if (size < 0)
38674fe6c29SRuslan Bukin return size;
38774fe6c29SRuslan Bukin
38874fe6c29SRuslan Bukin packet->type = ppt_tip_pge;
38974fe6c29SRuslan Bukin packet->size = (uint8_t) size;
39074fe6c29SRuslan Bukin
39174fe6c29SRuslan Bukin return size;
39274fe6c29SRuslan Bukin }
39374fe6c29SRuslan Bukin
pt_pkt_decode_tip_pgd(struct pt_packet_decoder * decoder,struct pt_packet * packet)39474fe6c29SRuslan Bukin int pt_pkt_decode_tip_pgd(struct pt_packet_decoder *decoder,
39574fe6c29SRuslan Bukin struct pt_packet *packet)
39674fe6c29SRuslan Bukin {
39774fe6c29SRuslan Bukin int size;
39874fe6c29SRuslan Bukin
39974fe6c29SRuslan Bukin if (!decoder || !packet)
40074fe6c29SRuslan Bukin return -pte_internal;
40174fe6c29SRuslan Bukin
40274fe6c29SRuslan Bukin size = pt_pkt_read_ip(&packet->payload.ip, decoder->pos,
40374fe6c29SRuslan Bukin &decoder->config);
40474fe6c29SRuslan Bukin if (size < 0)
40574fe6c29SRuslan Bukin return size;
40674fe6c29SRuslan Bukin
40774fe6c29SRuslan Bukin packet->type = ppt_tip_pgd;
40874fe6c29SRuslan Bukin packet->size = (uint8_t) size;
40974fe6c29SRuslan Bukin
41074fe6c29SRuslan Bukin return size;
41174fe6c29SRuslan Bukin }
41274fe6c29SRuslan Bukin
pt_pkt_decode_fup(struct pt_packet_decoder * decoder,struct pt_packet * packet)41374fe6c29SRuslan Bukin int pt_pkt_decode_fup(struct pt_packet_decoder *decoder,
41474fe6c29SRuslan Bukin struct pt_packet *packet)
41574fe6c29SRuslan Bukin {
41674fe6c29SRuslan Bukin int size;
41774fe6c29SRuslan Bukin
41874fe6c29SRuslan Bukin if (!decoder || !packet)
41974fe6c29SRuslan Bukin return -pte_internal;
42074fe6c29SRuslan Bukin
42174fe6c29SRuslan Bukin size = pt_pkt_read_ip(&packet->payload.ip, decoder->pos,
42274fe6c29SRuslan Bukin &decoder->config);
42374fe6c29SRuslan Bukin if (size < 0)
42474fe6c29SRuslan Bukin return size;
42574fe6c29SRuslan Bukin
42674fe6c29SRuslan Bukin packet->type = ppt_fup;
42774fe6c29SRuslan Bukin packet->size = (uint8_t) size;
42874fe6c29SRuslan Bukin
42974fe6c29SRuslan Bukin return size;
43074fe6c29SRuslan Bukin }
43174fe6c29SRuslan Bukin
pt_pkt_decode_pip(struct pt_packet_decoder * decoder,struct pt_packet * packet)43274fe6c29SRuslan Bukin int pt_pkt_decode_pip(struct pt_packet_decoder *decoder,
43374fe6c29SRuslan Bukin struct pt_packet *packet)
43474fe6c29SRuslan Bukin {
43574fe6c29SRuslan Bukin int size;
43674fe6c29SRuslan Bukin
43774fe6c29SRuslan Bukin if (!decoder || !packet)
43874fe6c29SRuslan Bukin return -pte_internal;
43974fe6c29SRuslan Bukin
44074fe6c29SRuslan Bukin size = pt_pkt_read_pip(&packet->payload.pip, decoder->pos,
44174fe6c29SRuslan Bukin &decoder->config);
44274fe6c29SRuslan Bukin if (size < 0)
44374fe6c29SRuslan Bukin return size;
44474fe6c29SRuslan Bukin
44574fe6c29SRuslan Bukin packet->type = ppt_pip;
44674fe6c29SRuslan Bukin packet->size = (uint8_t) size;
44774fe6c29SRuslan Bukin
44874fe6c29SRuslan Bukin return size;
44974fe6c29SRuslan Bukin }
45074fe6c29SRuslan Bukin
pt_pkt_decode_ovf(struct pt_packet_decoder * decoder,struct pt_packet * packet)45174fe6c29SRuslan Bukin int pt_pkt_decode_ovf(struct pt_packet_decoder *decoder,
45274fe6c29SRuslan Bukin struct pt_packet *packet)
45374fe6c29SRuslan Bukin {
45474fe6c29SRuslan Bukin (void) decoder;
45574fe6c29SRuslan Bukin
45674fe6c29SRuslan Bukin if (!packet)
45774fe6c29SRuslan Bukin return -pte_internal;
45874fe6c29SRuslan Bukin
45974fe6c29SRuslan Bukin packet->type = ppt_ovf;
46074fe6c29SRuslan Bukin packet->size = ptps_ovf;
46174fe6c29SRuslan Bukin
46274fe6c29SRuslan Bukin return ptps_ovf;
46374fe6c29SRuslan Bukin }
46474fe6c29SRuslan Bukin
pt_pkt_decode_mode(struct pt_packet_decoder * decoder,struct pt_packet * packet)46574fe6c29SRuslan Bukin int pt_pkt_decode_mode(struct pt_packet_decoder *decoder,
46674fe6c29SRuslan Bukin struct pt_packet *packet)
46774fe6c29SRuslan Bukin {
46874fe6c29SRuslan Bukin int size;
46974fe6c29SRuslan Bukin
47074fe6c29SRuslan Bukin if (!decoder || !packet)
47174fe6c29SRuslan Bukin return -pte_internal;
47274fe6c29SRuslan Bukin
47374fe6c29SRuslan Bukin size = pt_pkt_read_mode(&packet->payload.mode, decoder->pos,
47474fe6c29SRuslan Bukin &decoder->config);
47574fe6c29SRuslan Bukin if (size < 0)
47674fe6c29SRuslan Bukin return size;
47774fe6c29SRuslan Bukin
47874fe6c29SRuslan Bukin packet->type = ppt_mode;
47974fe6c29SRuslan Bukin packet->size = (uint8_t) size;
48074fe6c29SRuslan Bukin
48174fe6c29SRuslan Bukin return size;
48274fe6c29SRuslan Bukin }
48374fe6c29SRuslan Bukin
pt_pkt_decode_psbend(struct pt_packet_decoder * decoder,struct pt_packet * packet)48474fe6c29SRuslan Bukin int pt_pkt_decode_psbend(struct pt_packet_decoder *decoder,
48574fe6c29SRuslan Bukin struct pt_packet *packet)
48674fe6c29SRuslan Bukin {
48774fe6c29SRuslan Bukin (void) decoder;
48874fe6c29SRuslan Bukin
48974fe6c29SRuslan Bukin if (!packet)
49074fe6c29SRuslan Bukin return -pte_internal;
49174fe6c29SRuslan Bukin
49274fe6c29SRuslan Bukin packet->type = ppt_psbend;
49374fe6c29SRuslan Bukin packet->size = ptps_psbend;
49474fe6c29SRuslan Bukin
49574fe6c29SRuslan Bukin return ptps_psbend;
49674fe6c29SRuslan Bukin }
49774fe6c29SRuslan Bukin
pt_pkt_decode_tsc(struct pt_packet_decoder * decoder,struct pt_packet * packet)49874fe6c29SRuslan Bukin int pt_pkt_decode_tsc(struct pt_packet_decoder *decoder,
49974fe6c29SRuslan Bukin struct pt_packet *packet)
50074fe6c29SRuslan Bukin {
50174fe6c29SRuslan Bukin int size;
50274fe6c29SRuslan Bukin
50374fe6c29SRuslan Bukin if (!decoder || !packet)
50474fe6c29SRuslan Bukin return -pte_internal;
50574fe6c29SRuslan Bukin
50674fe6c29SRuslan Bukin size = pt_pkt_read_tsc(&packet->payload.tsc, decoder->pos,
50774fe6c29SRuslan Bukin &decoder->config);
50874fe6c29SRuslan Bukin if (size < 0)
50974fe6c29SRuslan Bukin return size;
51074fe6c29SRuslan Bukin
51174fe6c29SRuslan Bukin packet->type = ppt_tsc;
51274fe6c29SRuslan Bukin packet->size = (uint8_t) size;
51374fe6c29SRuslan Bukin
51474fe6c29SRuslan Bukin return size;
51574fe6c29SRuslan Bukin }
51674fe6c29SRuslan Bukin
pt_pkt_decode_cbr(struct pt_packet_decoder * decoder,struct pt_packet * packet)51774fe6c29SRuslan Bukin int pt_pkt_decode_cbr(struct pt_packet_decoder *decoder,
51874fe6c29SRuslan Bukin struct pt_packet *packet)
51974fe6c29SRuslan Bukin {
52074fe6c29SRuslan Bukin int size;
52174fe6c29SRuslan Bukin
52274fe6c29SRuslan Bukin if (!decoder || !packet)
52374fe6c29SRuslan Bukin return -pte_internal;
52474fe6c29SRuslan Bukin
52574fe6c29SRuslan Bukin size = pt_pkt_read_cbr(&packet->payload.cbr, decoder->pos,
52674fe6c29SRuslan Bukin &decoder->config);
52774fe6c29SRuslan Bukin if (size < 0)
52874fe6c29SRuslan Bukin return size;
52974fe6c29SRuslan Bukin
53074fe6c29SRuslan Bukin packet->type = ppt_cbr;
53174fe6c29SRuslan Bukin packet->size = (uint8_t) size;
53274fe6c29SRuslan Bukin
53374fe6c29SRuslan Bukin return size;
53474fe6c29SRuslan Bukin }
53574fe6c29SRuslan Bukin
pt_pkt_decode_tma(struct pt_packet_decoder * decoder,struct pt_packet * packet)53674fe6c29SRuslan Bukin int pt_pkt_decode_tma(struct pt_packet_decoder *decoder,
53774fe6c29SRuslan Bukin struct pt_packet *packet)
53874fe6c29SRuslan Bukin {
53974fe6c29SRuslan Bukin int size;
54074fe6c29SRuslan Bukin
54174fe6c29SRuslan Bukin if (!decoder || !packet)
54274fe6c29SRuslan Bukin return -pte_internal;
54374fe6c29SRuslan Bukin
54474fe6c29SRuslan Bukin size = pt_pkt_read_tma(&packet->payload.tma, decoder->pos,
54574fe6c29SRuslan Bukin &decoder->config);
54674fe6c29SRuslan Bukin if (size < 0)
54774fe6c29SRuslan Bukin return size;
54874fe6c29SRuslan Bukin
54974fe6c29SRuslan Bukin packet->type = ppt_tma;
55074fe6c29SRuslan Bukin packet->size = (uint8_t) size;
55174fe6c29SRuslan Bukin
55274fe6c29SRuslan Bukin return size;
55374fe6c29SRuslan Bukin }
55474fe6c29SRuslan Bukin
pt_pkt_decode_mtc(struct pt_packet_decoder * decoder,struct pt_packet * packet)55574fe6c29SRuslan Bukin int pt_pkt_decode_mtc(struct pt_packet_decoder *decoder,
55674fe6c29SRuslan Bukin struct pt_packet *packet)
55774fe6c29SRuslan Bukin {
55874fe6c29SRuslan Bukin int size;
55974fe6c29SRuslan Bukin
56074fe6c29SRuslan Bukin if (!decoder || !packet)
56174fe6c29SRuslan Bukin return -pte_internal;
56274fe6c29SRuslan Bukin
56374fe6c29SRuslan Bukin size = pt_pkt_read_mtc(&packet->payload.mtc, decoder->pos,
56474fe6c29SRuslan Bukin &decoder->config);
56574fe6c29SRuslan Bukin if (size < 0)
56674fe6c29SRuslan Bukin return size;
56774fe6c29SRuslan Bukin
56874fe6c29SRuslan Bukin packet->type = ppt_mtc;
56974fe6c29SRuslan Bukin packet->size = (uint8_t) size;
57074fe6c29SRuslan Bukin
57174fe6c29SRuslan Bukin return size;
57274fe6c29SRuslan Bukin }
57374fe6c29SRuslan Bukin
pt_pkt_decode_cyc(struct pt_packet_decoder * decoder,struct pt_packet * packet)57474fe6c29SRuslan Bukin int pt_pkt_decode_cyc(struct pt_packet_decoder *decoder,
57574fe6c29SRuslan Bukin struct pt_packet *packet)
57674fe6c29SRuslan Bukin {
57774fe6c29SRuslan Bukin int size;
57874fe6c29SRuslan Bukin
57974fe6c29SRuslan Bukin if (!decoder || !packet)
58074fe6c29SRuslan Bukin return -pte_internal;
58174fe6c29SRuslan Bukin
58274fe6c29SRuslan Bukin size = pt_pkt_read_cyc(&packet->payload.cyc, decoder->pos,
58374fe6c29SRuslan Bukin &decoder->config);
58474fe6c29SRuslan Bukin if (size < 0)
58574fe6c29SRuslan Bukin return size;
58674fe6c29SRuslan Bukin
58774fe6c29SRuslan Bukin packet->type = ppt_cyc;
58874fe6c29SRuslan Bukin packet->size = (uint8_t) size;
58974fe6c29SRuslan Bukin
59074fe6c29SRuslan Bukin return size;
59174fe6c29SRuslan Bukin }
59274fe6c29SRuslan Bukin
pt_pkt_decode_stop(struct pt_packet_decoder * decoder,struct pt_packet * packet)59374fe6c29SRuslan Bukin int pt_pkt_decode_stop(struct pt_packet_decoder *decoder,
59474fe6c29SRuslan Bukin struct pt_packet *packet)
59574fe6c29SRuslan Bukin {
59674fe6c29SRuslan Bukin (void) decoder;
59774fe6c29SRuslan Bukin
59874fe6c29SRuslan Bukin if (!packet)
59974fe6c29SRuslan Bukin return -pte_internal;
60074fe6c29SRuslan Bukin
60174fe6c29SRuslan Bukin packet->type = ppt_stop;
60274fe6c29SRuslan Bukin packet->size = ptps_stop;
60374fe6c29SRuslan Bukin
60474fe6c29SRuslan Bukin return ptps_stop;
60574fe6c29SRuslan Bukin }
60674fe6c29SRuslan Bukin
pt_pkt_decode_vmcs(struct pt_packet_decoder * decoder,struct pt_packet * packet)60774fe6c29SRuslan Bukin int pt_pkt_decode_vmcs(struct pt_packet_decoder *decoder,
60874fe6c29SRuslan Bukin struct pt_packet *packet)
60974fe6c29SRuslan Bukin {
61074fe6c29SRuslan Bukin int size;
61174fe6c29SRuslan Bukin
61274fe6c29SRuslan Bukin if (!decoder || !packet)
61374fe6c29SRuslan Bukin return -pte_internal;
61474fe6c29SRuslan Bukin
61574fe6c29SRuslan Bukin size = pt_pkt_read_vmcs(&packet->payload.vmcs, decoder->pos,
61674fe6c29SRuslan Bukin &decoder->config);
61774fe6c29SRuslan Bukin if (size < 0)
61874fe6c29SRuslan Bukin return size;
61974fe6c29SRuslan Bukin
62074fe6c29SRuslan Bukin packet->type = ppt_vmcs;
62174fe6c29SRuslan Bukin packet->size = (uint8_t) size;
62274fe6c29SRuslan Bukin
62374fe6c29SRuslan Bukin return size;
62474fe6c29SRuslan Bukin }
62574fe6c29SRuslan Bukin
pt_pkt_decode_mnt(struct pt_packet_decoder * decoder,struct pt_packet * packet)62674fe6c29SRuslan Bukin int pt_pkt_decode_mnt(struct pt_packet_decoder *decoder,
62774fe6c29SRuslan Bukin struct pt_packet *packet)
62874fe6c29SRuslan Bukin {
62974fe6c29SRuslan Bukin int size;
63074fe6c29SRuslan Bukin
63174fe6c29SRuslan Bukin if (!decoder || !packet)
63274fe6c29SRuslan Bukin return -pte_internal;
63374fe6c29SRuslan Bukin
63474fe6c29SRuslan Bukin size = pt_pkt_read_mnt(&packet->payload.mnt, decoder->pos,
63574fe6c29SRuslan Bukin &decoder->config);
63674fe6c29SRuslan Bukin if (size < 0)
63774fe6c29SRuslan Bukin return size;
63874fe6c29SRuslan Bukin
63974fe6c29SRuslan Bukin packet->type = ppt_mnt;
64074fe6c29SRuslan Bukin packet->size = (uint8_t) size;
64174fe6c29SRuslan Bukin
64274fe6c29SRuslan Bukin return size;
64374fe6c29SRuslan Bukin }
64474fe6c29SRuslan Bukin
pt_pkt_decode_exstop(struct pt_packet_decoder * decoder,struct pt_packet * packet)64574fe6c29SRuslan Bukin int pt_pkt_decode_exstop(struct pt_packet_decoder *decoder,
64674fe6c29SRuslan Bukin struct pt_packet *packet)
64774fe6c29SRuslan Bukin {
64874fe6c29SRuslan Bukin int size;
64974fe6c29SRuslan Bukin
65074fe6c29SRuslan Bukin if (!decoder || !packet)
65174fe6c29SRuslan Bukin return -pte_internal;
65274fe6c29SRuslan Bukin
65374fe6c29SRuslan Bukin size = pt_pkt_read_exstop(&packet->payload.exstop, decoder->pos,
65474fe6c29SRuslan Bukin &decoder->config);
65574fe6c29SRuslan Bukin if (size < 0)
65674fe6c29SRuslan Bukin return size;
65774fe6c29SRuslan Bukin
65874fe6c29SRuslan Bukin packet->type = ppt_exstop;
65974fe6c29SRuslan Bukin packet->size = (uint8_t) size;
66074fe6c29SRuslan Bukin
66174fe6c29SRuslan Bukin return size;
66274fe6c29SRuslan Bukin }
66374fe6c29SRuslan Bukin
pt_pkt_decode_mwait(struct pt_packet_decoder * decoder,struct pt_packet * packet)66474fe6c29SRuslan Bukin int pt_pkt_decode_mwait(struct pt_packet_decoder *decoder,
66574fe6c29SRuslan Bukin struct pt_packet *packet)
66674fe6c29SRuslan Bukin {
66774fe6c29SRuslan Bukin int size;
66874fe6c29SRuslan Bukin
66974fe6c29SRuslan Bukin if (!decoder || !packet)
67074fe6c29SRuslan Bukin return -pte_internal;
67174fe6c29SRuslan Bukin
67274fe6c29SRuslan Bukin size = pt_pkt_read_mwait(&packet->payload.mwait, decoder->pos,
67374fe6c29SRuslan Bukin &decoder->config);
67474fe6c29SRuslan Bukin if (size < 0)
67574fe6c29SRuslan Bukin return size;
67674fe6c29SRuslan Bukin
67774fe6c29SRuslan Bukin packet->type = ppt_mwait;
67874fe6c29SRuslan Bukin packet->size = (uint8_t) size;
67974fe6c29SRuslan Bukin
68074fe6c29SRuslan Bukin return size;
68174fe6c29SRuslan Bukin }
68274fe6c29SRuslan Bukin
pt_pkt_decode_pwre(struct pt_packet_decoder * decoder,struct pt_packet * packet)68374fe6c29SRuslan Bukin int pt_pkt_decode_pwre(struct pt_packet_decoder *decoder,
68474fe6c29SRuslan Bukin struct pt_packet *packet)
68574fe6c29SRuslan Bukin {
68674fe6c29SRuslan Bukin int size;
68774fe6c29SRuslan Bukin
68874fe6c29SRuslan Bukin if (!decoder || !packet)
68974fe6c29SRuslan Bukin return -pte_internal;
69074fe6c29SRuslan Bukin
69174fe6c29SRuslan Bukin size = pt_pkt_read_pwre(&packet->payload.pwre, decoder->pos,
69274fe6c29SRuslan Bukin &decoder->config);
69374fe6c29SRuslan Bukin if (size < 0)
69474fe6c29SRuslan Bukin return size;
69574fe6c29SRuslan Bukin
69674fe6c29SRuslan Bukin packet->type = ppt_pwre;
69774fe6c29SRuslan Bukin packet->size = (uint8_t) size;
69874fe6c29SRuslan Bukin
69974fe6c29SRuslan Bukin return size;
70074fe6c29SRuslan Bukin }
70174fe6c29SRuslan Bukin
pt_pkt_decode_pwrx(struct pt_packet_decoder * decoder,struct pt_packet * packet)70274fe6c29SRuslan Bukin int pt_pkt_decode_pwrx(struct pt_packet_decoder *decoder,
70374fe6c29SRuslan Bukin struct pt_packet *packet)
70474fe6c29SRuslan Bukin {
70574fe6c29SRuslan Bukin int size;
70674fe6c29SRuslan Bukin
70774fe6c29SRuslan Bukin if (!decoder || !packet)
70874fe6c29SRuslan Bukin return -pte_internal;
70974fe6c29SRuslan Bukin
71074fe6c29SRuslan Bukin size = pt_pkt_read_pwrx(&packet->payload.pwrx, decoder->pos,
71174fe6c29SRuslan Bukin &decoder->config);
71274fe6c29SRuslan Bukin if (size < 0)
71374fe6c29SRuslan Bukin return size;
71474fe6c29SRuslan Bukin
71574fe6c29SRuslan Bukin packet->type = ppt_pwrx;
71674fe6c29SRuslan Bukin packet->size = (uint8_t) size;
71774fe6c29SRuslan Bukin
71874fe6c29SRuslan Bukin return size;
71974fe6c29SRuslan Bukin }
72074fe6c29SRuslan Bukin
pt_pkt_decode_ptw(struct pt_packet_decoder * decoder,struct pt_packet * packet)72174fe6c29SRuslan Bukin int pt_pkt_decode_ptw(struct pt_packet_decoder *decoder,
72274fe6c29SRuslan Bukin struct pt_packet *packet)
72374fe6c29SRuslan Bukin {
72474fe6c29SRuslan Bukin int size;
72574fe6c29SRuslan Bukin
72674fe6c29SRuslan Bukin if (!decoder || !packet)
72774fe6c29SRuslan Bukin return -pte_internal;
72874fe6c29SRuslan Bukin
72974fe6c29SRuslan Bukin size = pt_pkt_read_ptw(&packet->payload.ptw, decoder->pos,
73074fe6c29SRuslan Bukin &decoder->config);
73174fe6c29SRuslan Bukin if (size < 0)
73274fe6c29SRuslan Bukin return size;
73374fe6c29SRuslan Bukin
73474fe6c29SRuslan Bukin packet->type = ppt_ptw;
73574fe6c29SRuslan Bukin packet->size = (uint8_t) size;
73674fe6c29SRuslan Bukin
73774fe6c29SRuslan Bukin return size;
73874fe6c29SRuslan Bukin }
739