diff --git a/content/research/decoding-fast-examples.md b/content/research/decoding-fast-examples.md index e884aee..b0812f3 100644 --- a/content/research/decoding-fast-examples.md +++ b/content/research/decoding-fast-examples.md @@ -134,45 +134,51 @@ list of users and their IDs. ## Processing As mentioned before, the first byte, `1100_0000` is the Presence Map of the -root element with the leading Template ID. There is only one bit set, which -means the Template ID is present. +root element. There is only one bit set, which means the Template ID is +present. -The second byte, `1000_0010` is the Template ID. Because it have the stop bit, -that's the only byte for it. Removing the high order bit gives us `000_0010`, -which is "2", so we know we are dealing with the "SequenceOfSequences" -template. +Because the Template ID is present in the Presence Map, we read the next byte, +`1000_0010`. Because this byte have the stop bit, we stop reading. Removing +this stop bit gives us `000_0010`, which is "2", so we know we are dealing with +the "SequenceOfSequences" template. Now that we have the template and know the fields, we know what to read. The -first field in our template is the sequence. The first thing we have in the +first field in our template is a sequence. The first thing we have in the sequence (and this is the first thing for *every* sequence) is the length of it. So we read the next byte, `1000_0011`, which is the only byte we need to read. It represents an unsigned int, which is "3", so this sequence have 3 -elements -- and using our description in the previous sections, we know now -that we have 3 groups. +records -- and using our description in the previous sections, we know now +that we have 3 user groups. One point here: Because all fields in this sequence don't have any operators, -it means the Presence Map doesn't exist. For sequences, every start of a new -record contains a Presence Map only if at least one of the fields in the -sequence require a Presence Map. That's not the case here. +the Presence Map is not necessary and, thus, it doesn't exist (or, better yet, +we shouldn't try to read something and assume it is a Presence Map). For +sequences, every start of a new record contains a Presence Map only if at least +one of the fields in the sequence require a Presence Map. That's not the case +here. Because there is no Presence Map for the "OuterSequence", the next bytes are the "GroupID" field. We should read everything till we find the stop bit, so we get `0000_0011`, `0010_0011`, `0001_1000` and `1110_0111`. For every byte we remove the high order bit and then join everything into a single thing, in this case `000_0011 010_0011 001_1000 110_0111` or simply -`0000_0110_1000_1100_1100_0110_0111`; this value, being an unsigned int, is -"6868070". Here is a good point to remind that, because the field is mandatory, -it means that's actually the value of "GroupID"; if the field as optional, the -actual value would be "6868069". +`0000_0110_1000_1100_1100_0110_0111`. This value, being an unsigned int, is +"6868070". + +{% note() %} +Here is a good point to remind that, because the field is mandatory, it means +that's actually the value of "GroupID"; if the field as optional, the actual +value would be "6868069". +{% end %} Now for he "InnerSequence" field. The first step is to gather the number of elements (the length of the sequence). That's the `1000_0010` byte, which is "2". So there are two users in this group. -Because "InnerSequence" has a field that uses the Presence Map ("ID" uses the -Increment operator, so we need to check if there is an incoming value for it or -we should just increment the value), the first thing after the length is the -Presence Map for this record. The byte `1100_0000` indicates that the first +Because "InnerSequence" has a field that needs the Presence Map ("ID" uses the +Increment operator, that we need either read the incoming value for it or we +should just increment the previous value), the first thing after the length is +the Presence Map for this record. The byte `1100_0000` indicates that the first field that requires a Presence Map is present. But that's not the time to use the Presence Map yet. The field after the length diff --git a/content/research/decoding-fast-examples.pt.md b/content/research/decoding-fast-examples.pt.md index a9455c0..0b7c460 100644 --- a/content/research/decoding-fast-examples.pt.md +++ b/content/research/decoding-fast-examples.pt.md @@ -52,17 +52,17 @@ Bytes: O primeiro byte é o Mapa de Presença. Removendo o bit de parada, temos `110_0000`. Esse Mapa de Presença tem um campo que não é descrito no template: -O ID do Template. Como o primeiro bit está ligado, nós sabemos que o ID está -lá. Ainda, tenha em mente que o ID do Template é o único campo que nós sabemos -que existe até agora; não existe nenhuma outra informação sobre o que é aquele -segundo bit no Mapa de Presença -- nós precisamos encontrar qual template vamos -usar antes de mais nada. - -O próximo byte é lido: `1000_0001`. Como mencionado acima, isso é o ID do -Template. Sendo um inteiro sem sinal (e provavelmente mandatório, mas não me -pergunte como isso funciona) e removendo o bit de parada, temos o inteiro "1", -que é exatamente o mesmo ID que temos no nosso template; agora nós sabemos -quais campos devem ser processados. +O Template ID (ID de Template). Como o primeiro bit está ligado, nós sabemos +que o ID está lá. Ainda, tenha em mente que o Template ID é o único campo que +nós sabemos que existe até agora; não existe nenhuma outra informação sobre o +que é aquele segundo bit no Mapa de Presença -- nós precisamos encontrar qual +template vamos usar antes de mais nada. + +O próximo byte é lido: `1000_0001`. Como mencionado acima, isso é o Template +ID. Sendo um inteiro sem sinal (e provavelmente mandatório, mas não me pergunte +como isso funciona) e removendo o bit de parada, temos o inteiro "1", que é +exatamente o mesmo ID que temos no nosso template; agora nós sabemos quais +campos devem ser processados. O primeiro campo do template é uma string com um valor default. Como o campo usa o operador Default, nós precisamos verificar se o valor está presente nos @@ -134,6 +134,64 @@ grupo, uma lista de usuários e seus IDs. ## Processamento +Como mencionado anteriormente, o primeiro byte, `1100_0000` é o Mapa de +Presença do elemento raiz. Existe apenas um bit ligado, o que indica que o +Template ID está presente. + +Como o Template ID está presente no Mapa de Presença, nós lemos o próximo byte +`1000_0010`. Como este byte tem o bit de parada, nós paramos de ler. Removendo +este bit, nós temos `000_0010`, que é "2", e agora sabemos que estamos lidando +com o template "SequenceOfSequences". + +Agora que temos o template e conhecemos os campos, nós sabemos o que precisamos +ler. O primeiro campo do nosso template é uma sequência. A primeira coisa que +nós temos em uma sequência (e é a primeira coisa em *todas* as sequências) é o +tamanho desta. Assim, nós lemos o próximo byte, `1000_0011`, que é o único byte +que precisamos ler. Ele representa um inteiro sem sinal, que é 3, então esta +sequência tem 3 registros -- e usando nossa descrição anterior, nós sabemos que +temos 3 grupos de usuários. + +Um ponto ser visto aqui: Como todos os campos desta sequência não tem qualquer +operador, o Mapa de Presença não é necessário e, assim, ele não existe (ou, +melhor, nós não devemos tentar ler alguma coisa e assumir que é o Mapa de +Presença). Para sequências, o começo de cada registro contém um Mapa de +Presença apenas se pelo menos um dos campos na sequência precisa do Mapa. O que +não é o caso aqui. + +Como não há Mapa de Presença para a sequência "OuterSequence", os próximos +bytes são o campo "GroupID". Nós devemos ler os bytes até encontrar o bit de +parada; assim, recebemos `0000_0011`, `0010_0011`, `0001_1000` e `1110_0111`. +Para cada byte nós removemos o bit de mais alta ordem (o bit de parada) e +juntamos tudo em uma única coisa, neste caso, `00_0011 010_0011 001_1000 +110_0111` ou simplesmente `0000_0110_1000_1100_1100_0110_0110`. Este valor, +sendo um inteiro sem sinal, é "6868070". + +{% note() %} +Aqui é um bom ponto para lembrar que, como o campo é mandatório, isto significa +que este é realmente o valor para "GroupID"; se o campo fosse opcional, o valor +de verdade seria "6868069". +{% end %} + +Agora para o campo "InnerSequence". O primeiro passo é recuperar o número de +elementos (o "length" da sequência). Esse é o byte `1000_0010`, que é 2. Assim, +há dois usuários neste grupo. + +Como o "InnerSequence" tem um campo que precisa do Mapa de Presença ("ID" usa o +operador Increment, o que indica que ou iremos ler o o valor vindo dos dados de +entrada ou iremos incrementar o valor anterior), o primeiro byte depois do +tamanho é o Mapa de Presença para este registro. O byte `1100_0000` indica que +o primeiro campo que precisa do Mapa de Presença está presente. + +Mas ainda não é o momento de usar o Mapa de Presença. O campo logo após o +tamanho é "Username", que é uma string mandatória. Strings mandatórias sem +operadores estão sempre presentes e nós não precisamos olhar o Mapa de +Presença. Assim como fizemos com "String" no exemplo anterior, nós lemos os +bytes até encontrar um com o bit de parada, mas não juntamos os mesmos: +`0101_0101` (85), `0111_0011` (115), `0110_0101` (101), `0111_0010` (114) e +`1011_0001` (49, se removermos o bit de parada), que convertidos pela tabela +ASCII nos dá o valor "User1". + +