mirror of
https://github.com/wader/fq.git
synced 2024-12-23 05:13:30 +03:00
Add to/bytes/bits[range]
This commit is contained in:
parent
a050adca49
commit
7f36f703dd
1
LICENSE
1
LICENSE
@ -1,4 +1,5 @@
|
||||
Copyright (c) 2021 Mattias Wadman
|
||||
colorjson fork and various code in gojqextra package Copyright (c) 2019-2021 itchyny
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy of
|
||||
this software and associated documentation files (the "Software"), to deal in
|
||||
|
14
doc/usage.md
14
doc/usage.md
@ -142,16 +142,22 @@ notable is support for arbitrary-precision integers.
|
||||
- `format_root/0` return root value of format for value
|
||||
- `parent/0` return parent value
|
||||
- `parents/0` output parents of value
|
||||
- `find` and `grep` all take 1 or 2 arguments. First is a scalar to match, where a string is
|
||||
treated as a regexp. A buffer will be matches exact bytes. Second argument is regexp
|
||||
flags with addition to "b" which will treat each byte in the input buffer as a rune, this
|
||||
- All `find` and `grep` functions take 1 or 2 arguments. First is a scalar to match, where a string is
|
||||
treated as a regexp. A buffer scalar will be matches exact bytes. Second argument are regexp
|
||||
flags with addition that "b" will treat each byte in the input buffer as a code point, this
|
||||
makes it possible to match exact bytes, ex: `find("\u00ff"; b")` will match the byte `0xff` and not
|
||||
the UTF-8 codepoint `0xff`.
|
||||
the UTF-8 encoded codepoint for 255.
|
||||
- `find/1`, `find/2` match in buffer and output match buffers
|
||||
- `grep/1`, `grep/2` recursively match value and buffer
|
||||
- `vgrep/1`, `vgrep/2` recursively match value
|
||||
- `bgrep/1`, `bgrep/2` recursively match buffer
|
||||
- `fgrep/1`, `fgrep/2` recursively match field name
|
||||
- Buffers:
|
||||
- `tobits` - Transform input into a bits buffer not preserving source range, will start at zero.
|
||||
- `tobitsrange` - Transform input into a bits buffer preserving source range if possible.
|
||||
- `tobytes` - Transform input into a bytes buffer not preserving source range, will start at zero.
|
||||
- `tobytesrange` - Transform input into a byte buffer preserving source range if possible.
|
||||
- `buffer[start:end]`, `buffer[:end]`, `buffer[start:]` - Create a sub buffer from start to end in buffer units preserving source range.
|
||||
- `open` open file for reading
|
||||
- `probe` or `decode` probe format and decode
|
||||
- `mp3`, `matroska`, ..., `<name>`, `decode([name])` force decode as format
|
||||
|
@ -1,17 +1,40 @@
|
||||
package gojqextra
|
||||
|
||||
import "fmt"
|
||||
import (
|
||||
"fmt"
|
||||
"math/big"
|
||||
|
||||
// many of these based on errors form gojq
|
||||
"github.com/wader/gojq"
|
||||
)
|
||||
|
||||
// many of these based on errors from gojq
|
||||
// TODO: refactor to use errors from gojq?
|
||||
// TODO: preview from gojq?
|
||||
|
||||
type NonUpdatableTypeError struct {
|
||||
Typ string
|
||||
Key string
|
||||
}
|
||||
|
||||
func (err NonUpdatableTypeError) Error() string {
|
||||
return fmt.Sprintf("update key %v cannot be applied to: %s", err.Key, err.Typ)
|
||||
}
|
||||
|
||||
type FuncTypeError struct {
|
||||
Name string
|
||||
V interface{}
|
||||
}
|
||||
|
||||
func (err FuncTypeError) Error() string { return err.Name + " cannot be applied to: " + typeof(err.V) }
|
||||
|
||||
type FuncTypeNameError struct {
|
||||
Name string
|
||||
Typ string
|
||||
}
|
||||
|
||||
func (err FuncTypeError) Error() string { return err.Name + " cannot be applied to: " + err.Typ }
|
||||
func (err FuncTypeNameError) Error() string {
|
||||
return err.Name + " cannot be applied to: " + err.Typ
|
||||
}
|
||||
|
||||
type ExpectedObjectError struct {
|
||||
Typ string
|
||||
@ -70,3 +93,24 @@ type ArrayIndexTooLargeError struct {
|
||||
func (err *ArrayIndexTooLargeError) Error() string {
|
||||
return fmt.Sprintf("array index too large: %v", err.V)
|
||||
}
|
||||
|
||||
func typeof(v interface{}) string {
|
||||
switch v := v.(type) {
|
||||
case nil:
|
||||
return "null"
|
||||
case bool:
|
||||
return "boolean"
|
||||
case int, float64, *big.Int:
|
||||
return "number"
|
||||
case string:
|
||||
return "string"
|
||||
case []interface{}:
|
||||
return "array"
|
||||
case map[string]interface{}:
|
||||
return "object"
|
||||
case gojq.JQValue:
|
||||
return fmt.Sprintf("JQValue(%s)", v.JQValueType())
|
||||
default:
|
||||
panic(fmt.Sprintf("invalid value: %v", v))
|
||||
}
|
||||
}
|
||||
|
12
internal/gojqextra/math.go
Normal file
12
internal/gojqextra/math.go
Normal file
@ -0,0 +1,12 @@
|
||||
// from gojq
|
||||
// The MIT License (MIT)
|
||||
// Copyright (c) 2019-2021 itchyny
|
||||
|
||||
package gojqextra
|
||||
|
||||
import "math/bits"
|
||||
|
||||
const (
|
||||
maxInt = 1<<(bits.UintSize-1) - 1 // math.MaxInt64 or math.MaxInt32
|
||||
minInt = -maxInt - 1 // math.MinInt64 or math.MinInt32
|
||||
)
|
127
internal/gojqextra/totype.go
Normal file
127
internal/gojqextra/totype.go
Normal file
@ -0,0 +1,127 @@
|
||||
// Some of these functions are based on gojq func.go functions
|
||||
// TODO: maybe should be exported from gojq fq branch instead?
|
||||
// The MIT License (MIT)
|
||||
// Copyright (c) 2019-2021 itchyny
|
||||
|
||||
package gojqextra
|
||||
|
||||
import (
|
||||
"math"
|
||||
"math/big"
|
||||
"strconv"
|
||||
|
||||
"github.com/wader/gojq"
|
||||
)
|
||||
|
||||
func ToString(x interface{}) (string, bool) {
|
||||
switch x := x.(type) {
|
||||
case string:
|
||||
return x, true
|
||||
case gojq.JQValue:
|
||||
return ToString(x.JQValueToGoJQ())
|
||||
default:
|
||||
return "", false
|
||||
}
|
||||
}
|
||||
|
||||
func ToObject(x interface{}) (map[string]interface{}, bool) {
|
||||
switch x := x.(type) {
|
||||
case map[string]interface{}:
|
||||
return x, true
|
||||
case gojq.JQValue:
|
||||
return ToObject(x.JQValueToGoJQ())
|
||||
default:
|
||||
return nil, false
|
||||
}
|
||||
}
|
||||
|
||||
func ToArray(x interface{}) ([]interface{}, bool) {
|
||||
switch x := x.(type) {
|
||||
case []interface{}:
|
||||
return x, true
|
||||
case gojq.JQValue:
|
||||
return ToArray(x.JQValueToGoJQ())
|
||||
default:
|
||||
return nil, false
|
||||
}
|
||||
}
|
||||
|
||||
func ToBoolean(x interface{}) (bool, bool) {
|
||||
switch x := x.(type) {
|
||||
case bool:
|
||||
return x, true
|
||||
case gojq.JQValue:
|
||||
return ToBoolean(x.JQValueToGoJQ())
|
||||
default:
|
||||
return false, false
|
||||
}
|
||||
}
|
||||
|
||||
func IsNull(x interface{}) bool {
|
||||
switch x := x.(type) {
|
||||
case nil:
|
||||
return true
|
||||
case gojq.JQValue:
|
||||
return IsNull(x.JQValueToGoJQ())
|
||||
default:
|
||||
return false
|
||||
}
|
||||
}
|
||||
|
||||
func ToInt(x interface{}) (int, bool) {
|
||||
switch x := x.(type) {
|
||||
case int:
|
||||
return x, true
|
||||
case float64:
|
||||
return floatToInt(x), true
|
||||
case *big.Int:
|
||||
if x.IsInt64() {
|
||||
if i := x.Int64(); minInt <= i && i <= maxInt {
|
||||
return int(i), true
|
||||
}
|
||||
}
|
||||
if x.Sign() > 0 {
|
||||
return maxInt, true
|
||||
}
|
||||
return minInt, true
|
||||
case gojq.JQValue:
|
||||
return ToInt(x.JQValueToGoJQ())
|
||||
default:
|
||||
return 0, false
|
||||
}
|
||||
}
|
||||
|
||||
func floatToInt(x float64) int {
|
||||
if minInt <= x && x <= maxInt {
|
||||
return int(x)
|
||||
}
|
||||
if x > 0 {
|
||||
return maxInt
|
||||
}
|
||||
return minInt
|
||||
}
|
||||
|
||||
func ToFloat(x interface{}) (float64, bool) {
|
||||
switch x := x.(type) {
|
||||
case int:
|
||||
return float64(x), true
|
||||
case float64:
|
||||
return x, true
|
||||
case *big.Int:
|
||||
return bigToFloat(x), true
|
||||
case gojq.JQValue:
|
||||
return ToFloat(x.JQValueToGoJQ())
|
||||
default:
|
||||
return 0.0, false
|
||||
}
|
||||
}
|
||||
|
||||
func bigToFloat(x *big.Int) float64 {
|
||||
if x.IsInt64() {
|
||||
return float64(x.Int64())
|
||||
}
|
||||
if f, err := strconv.ParseFloat(x.String(), 64); err == nil {
|
||||
return f
|
||||
}
|
||||
return math.Inf(x.Sign())
|
||||
}
|
@ -23,15 +23,6 @@ func expectedArrayOrObject(key interface{}, typ string) error {
|
||||
}
|
||||
}
|
||||
|
||||
type NonUpdatableTypeError struct {
|
||||
Typ string
|
||||
Key string
|
||||
}
|
||||
|
||||
func (err NonUpdatableTypeError) Error() string {
|
||||
return fmt.Sprintf("update key %v cannot be applied to: %s", err.Key, err.Typ)
|
||||
}
|
||||
|
||||
// array
|
||||
|
||||
var _ gojq.JQValue = Array{}
|
||||
@ -86,7 +77,8 @@ func (v Array) JQValueUpdate(key interface{}, u interface{}, delpath bool) inter
|
||||
if delpath {
|
||||
return v
|
||||
}
|
||||
return FuncTypeError{Name: "setpath", Typ: "number"}
|
||||
// TODO: wrong error?
|
||||
return FuncTypeNameError{Name: "setpath", Typ: "number"}
|
||||
} else if intKey < 0 {
|
||||
intKey += len(v)
|
||||
}
|
||||
@ -111,10 +103,10 @@ func (v Array) JQValueHas(key interface{}) interface{} {
|
||||
}
|
||||
func (v Array) JQValueType() string { return "array" }
|
||||
func (v Array) JQValueToNumber() interface{} {
|
||||
return FuncTypeError{Name: "tonumber", Typ: "array"}
|
||||
return FuncTypeNameError{Name: "tonumber", Typ: "array"}
|
||||
}
|
||||
func (v Array) JQValueToString() interface{} {
|
||||
return FuncTypeError{Name: "tostring", Typ: "array"}
|
||||
return FuncTypeNameError{Name: "tostring", Typ: "array"}
|
||||
}
|
||||
func (v Array) JQValueToGoJQ() interface{} { return []interface{}(v) }
|
||||
|
||||
@ -177,10 +169,10 @@ func (v Object) JQValueHas(key interface{}) interface{} {
|
||||
}
|
||||
func (v Object) JQValueType() string { return "object" }
|
||||
func (v Object) JQValueToNumber() interface{} {
|
||||
return FuncTypeError{Name: "tonumber", Typ: "object"}
|
||||
return FuncTypeNameError{Name: "tonumber", Typ: "object"}
|
||||
}
|
||||
func (v Object) JQValueToString() interface{} {
|
||||
return FuncTypeError{Name: "tostring", Typ: "object"}
|
||||
return FuncTypeNameError{Name: "tostring", Typ: "object"}
|
||||
}
|
||||
func (v Object) JQValueToGoJQ() interface{} { return map[string]interface{}(v) }
|
||||
|
||||
@ -203,9 +195,9 @@ func (v Number) JQValueUpdate(key interface{}, u interface{}, delpath bool) inte
|
||||
return expectedArrayOrObject(key, "number")
|
||||
}
|
||||
func (v Number) JQValueEach() interface{} { return IteratorError{Typ: "number"} }
|
||||
func (v Number) JQValueKeys() interface{} { return FuncTypeError{Name: "keys", Typ: "number"} }
|
||||
func (v Number) JQValueKeys() interface{} { return FuncTypeNameError{Name: "keys", Typ: "number"} }
|
||||
func (v Number) JQValueHas(key interface{}) interface{} {
|
||||
return FuncTypeError{Name: "has", Typ: "number"}
|
||||
return FuncTypeNameError{Name: "has", Typ: "number"}
|
||||
}
|
||||
func (v Number) JQValueType() string { return "number" }
|
||||
func (v Number) JQValueToNumber() interface{} { return v.V }
|
||||
@ -240,9 +232,9 @@ func (v String) JQValueUpdate(key interface{}, u interface{}, delpath bool) inte
|
||||
return expectedArrayOrObject(key, "string")
|
||||
}
|
||||
func (v String) JQValueEach() interface{} { return IteratorError{Typ: "string"} }
|
||||
func (v String) JQValueKeys() interface{} { return FuncTypeError{Name: "keys", Typ: "string"} }
|
||||
func (v String) JQValueKeys() interface{} { return FuncTypeNameError{Name: "keys", Typ: "string"} }
|
||||
func (v String) JQValueHas(key interface{}) interface{} {
|
||||
return FuncTypeError{Name: "has", Typ: "string"}
|
||||
return FuncTypeNameError{Name: "has", Typ: "string"}
|
||||
}
|
||||
func (v String) JQValueType() string { return "string" }
|
||||
func (v String) JQValueToNumber() interface{} { return gojq.NormalizeNumbers(string(v)) }
|
||||
@ -255,7 +247,9 @@ var _ gojq.JQValue = Boolean(true)
|
||||
|
||||
type Boolean bool
|
||||
|
||||
func (v Boolean) JQValueLength() interface{} { return FuncTypeError{Name: "length", Typ: "boolean"} }
|
||||
func (v Boolean) JQValueLength() interface{} {
|
||||
return FuncTypeNameError{Name: "length", Typ: "boolean"}
|
||||
}
|
||||
func (v Boolean) JQValueSliceLen() interface{} { return ExpectedArrayError{Typ: "boolean"} }
|
||||
func (v Boolean) JQValueIndex(index int) interface{} { return ExpectedArrayError{Typ: "boolean"} }
|
||||
func (v Boolean) JQValueSlice(start int, end int) interface{} {
|
||||
@ -266,13 +260,13 @@ func (v Boolean) JQValueUpdate(key interface{}, u interface{}, delpath bool) int
|
||||
return expectedArrayOrObject(key, "boolean")
|
||||
}
|
||||
func (v Boolean) JQValueEach() interface{} { return IteratorError{Typ: "boolean"} }
|
||||
func (v Boolean) JQValueKeys() interface{} { return FuncTypeError{Name: "keys", Typ: "boolean"} }
|
||||
func (v Boolean) JQValueKeys() interface{} { return FuncTypeNameError{Name: "keys", Typ: "boolean"} }
|
||||
func (v Boolean) JQValueHas(key interface{}) interface{} {
|
||||
return FuncTypeError{Name: "has", Typ: "boolean"}
|
||||
return FuncTypeNameError{Name: "has", Typ: "boolean"}
|
||||
}
|
||||
func (v Boolean) JQValueType() string { return "boolean" }
|
||||
func (v Boolean) JQValueToNumber() interface{} {
|
||||
return FuncTypeError{Name: "tonumber", Typ: "boolean"}
|
||||
return FuncTypeNameError{Name: "tonumber", Typ: "boolean"}
|
||||
}
|
||||
func (v Boolean) JQValueToString() interface{} {
|
||||
if v {
|
||||
@ -297,10 +291,12 @@ func (v Null) JQValueUpdate(key interface{}, u interface{}, delpath bool) interf
|
||||
return expectedArrayOrObject(key, "null")
|
||||
}
|
||||
func (v Null) JQValueEach() interface{} { return IteratorError{Typ: "null"} }
|
||||
func (v Null) JQValueKeys() interface{} { return FuncTypeError{Name: "keys", Typ: "null"} }
|
||||
func (v Null) JQValueHas(key interface{}) interface{} { return FuncTypeError{Name: "has", Typ: "null"} }
|
||||
func (v Null) JQValueKeys() interface{} { return FuncTypeNameError{Name: "keys", Typ: "null"} }
|
||||
func (v Null) JQValueHas(key interface{}) interface{} {
|
||||
return FuncTypeNameError{Name: "has", Typ: "null"}
|
||||
}
|
||||
func (v Null) JQValueType() string { return "null" }
|
||||
func (v Null) JQValueToNumber() interface{} { return FuncTypeError{Name: "tonumber", Typ: "null"} }
|
||||
func (v Null) JQValueToNumber() interface{} { return FuncTypeNameError{Name: "tonumber", Typ: "null"} }
|
||||
func (v Null) JQValueToString() interface{} { return "null" }
|
||||
func (v Null) JQValueToGoJQ() interface{} { return nil }
|
||||
|
||||
@ -325,11 +321,11 @@ func (v Base) JQValueUpdate(key interface{}, u interface{}, delpath bool) interf
|
||||
return expectedArrayOrObject(key, v.Typ)
|
||||
}
|
||||
func (v Base) JQValueEach() interface{} { return IteratorError{Typ: v.Typ} }
|
||||
func (v Base) JQValueKeys() interface{} { return FuncTypeError{Name: "keys", Typ: v.Typ} }
|
||||
func (v Base) JQValueKeys() interface{} { return FuncTypeNameError{Name: "keys", Typ: v.Typ} }
|
||||
func (v Base) JQValueHas(key interface{}) interface{} {
|
||||
return HasKeyTypeError{L: "array", R: fmt.Sprintf("%v", key)}
|
||||
}
|
||||
func (v Base) JQValueType() string { return v.Typ }
|
||||
func (v Base) JQValueToNumber() interface{} { return FuncTypeError{Name: "tonumber", Typ: v.Typ} }
|
||||
func (v Base) JQValueToString() interface{} { return FuncTypeError{Name: "tostring", Typ: v.Typ} }
|
||||
func (v Base) JQValueToNumber() interface{} { return FuncTypeNameError{Name: "tonumber", Typ: v.Typ} }
|
||||
func (v Base) JQValueToString() interface{} { return FuncTypeNameError{Name: "tostring", Typ: v.Typ} }
|
||||
func (v Base) JQValueToGoJQ() interface{} { return nil }
|
@ -116,7 +116,7 @@ func (bv BufferView) JQValueType() string {
|
||||
return "buffer"
|
||||
}
|
||||
func (bv BufferView) JQValueKeys() interface{} {
|
||||
return gojqextra.FuncTypeError{Name: "keys", Typ: "buffer"}
|
||||
return gojqextra.FuncTypeNameError{Name: "keys", Typ: "buffer"}
|
||||
}
|
||||
func (bv BufferView) JQValueHas(key interface{}) interface{} {
|
||||
return gojqextra.HasKeyTypeError{L: "buffer", R: fmt.Sprintf("%v", key)}
|
||||
|
@ -60,8 +60,8 @@ func (i *Interp) makeFunctions() []Function {
|
||||
{[]string{"_display"}, 1, 1, nil, i._display},
|
||||
{[]string{"_hexdump"}, 1, 1, nil, i._hexdump},
|
||||
|
||||
{[]string{"tobytes"}, 0, 0, i.toBytes, nil},
|
||||
{[]string{"tobits"}, 0, 0, i.toBits, nil},
|
||||
{[]string{"_tobitsrange"}, 0, 2, i._toBitsRange, nil},
|
||||
|
||||
{[]string{"tovalue"}, 0, 1, i.toValue, nil},
|
||||
|
||||
{[]string{"hex"}, 0, 0, makeStringBitBufTransformFn(
|
||||
@ -700,20 +700,44 @@ func (i *Interp) _display(c interface{}, a []interface{}) gojq.Iter {
|
||||
}
|
||||
}
|
||||
|
||||
func (i *Interp) toBytes(c interface{}, a []interface{}) interface{} {
|
||||
bb, err := toBuffer(c)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
return bufferViewFromBuffer(bb, 8)
|
||||
}
|
||||
// note is used to implement tobytes*/0 also
|
||||
func (i *Interp) _toBitsRange(c interface{}, a []interface{}) interface{} {
|
||||
var unit int
|
||||
var r bool
|
||||
var ok bool
|
||||
|
||||
func (i *Interp) toBits(c interface{}, a []interface{}) interface{} {
|
||||
bb, err := toBuffer(c)
|
||||
if len(a) >= 1 {
|
||||
unit, ok = gojqextra.ToInt(a[0])
|
||||
if !ok {
|
||||
return gojqextra.FuncTypeError{Name: "_tobitsrange", V: a[0]}
|
||||
}
|
||||
} else {
|
||||
unit = 1
|
||||
}
|
||||
|
||||
if len(a) >= 2 {
|
||||
r, ok = gojqextra.ToBoolean(a[1])
|
||||
if !ok {
|
||||
return gojqextra.FuncTypeError{Name: "_tobitsrange", V: a[1]}
|
||||
}
|
||||
} else {
|
||||
r = true
|
||||
}
|
||||
|
||||
// TODO: unit > 8?
|
||||
|
||||
bv, err := toBufferView(c)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
return bufferViewFromBuffer(bb, 1)
|
||||
bv.unit = unit
|
||||
|
||||
if !r {
|
||||
bb, _ := bv.toBuffer()
|
||||
return bufferViewFromBuffer(bb, unit)
|
||||
}
|
||||
|
||||
return bv
|
||||
}
|
||||
|
||||
func (i *Interp) toValue(c interface{}, a []interface{}) interface{} {
|
||||
@ -838,7 +862,7 @@ func (i *Interp) find(c interface{}, a []interface{}) gojq.Iter {
|
||||
if len(a) > 1 {
|
||||
flags, ok = a[1].(string)
|
||||
if !ok {
|
||||
return gojq.NewIter(gojqextra.FuncTypeError{Name: "find", Typ: "string"})
|
||||
return gojq.NewIter(gojqextra.FuncTypeNameError{Name: "find", Typ: "string"})
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -51,6 +51,11 @@ def parents:
|
||||
end
|
||||
);
|
||||
|
||||
def tobitsrange: _tobitsrange;
|
||||
def tobytesrange: _tobitsrange(8);
|
||||
def tobits: _tobitsrange(1; false);
|
||||
def tobytes: _tobitsrange(8; false);
|
||||
|
||||
def formats:
|
||||
_registry.formats;
|
||||
|
||||
|
182
pkg/interp/testdata/buffer.fqtest
vendored
182
pkg/interp/testdata/buffer.fqtest
vendored
@ -55,3 +55,185 @@ error: buffer byte list must be bytes (0-255) got -1
|
||||
mp3> [256] | tobytes
|
||||
error: buffer byte list must be bytes (0-255) got 256
|
||||
mp3> ^D
|
||||
$ fq -d mp3 -i . /test.mp3
|
||||
mp3> .frames[1] | tobits | ., .start, .stop, .size, .[4:17], (tobits, tobytes, tobitsrange, tobytesrange | ., .start, .stop, .size, .[4:17])
|
||||
|00 01 02 03 04 05 06 07 08 09 0a 0b 0c 0d 0e 0f|0123456789abcdef|
|
||||
0x00|ff fb 50 c4 00 00 0a 2c 43 2e 55 94 80 01 80 93|..P....,C.U.....|.: none 0x0-0xcf.7 (208)
|
||||
* |until 0xcf.7 (end) (208) | |
|
||||
0
|
||||
1664
|
||||
1664
|
||||
|00 01 02 03 04 05 06 07 08 09 0a 0b 0c 0d 0e 0f|0123456789abcdef|
|
||||
0x0|ff fb 50 |..P |.: none 0x0.4-0x2 (1.5)
|
||||
|00 01 02 03 04 05 06 07 08 09 0a 0b 0c 0d 0e 0f|0123456789abcdef|
|
||||
0x00|ff fb 50 c4 00 00 0a 2c 43 2e 55 94 80 01 80 93|..P....,C.U.....|.: none 0x0-0xcf.7 (208)
|
||||
* |until 0xcf.7 (end) (208) | |
|
||||
0
|
||||
1664
|
||||
1664
|
||||
|00 01 02 03 04 05 06 07 08 09 0a 0b 0c 0d 0e 0f|0123456789abcdef|
|
||||
0x0|ff fb 50 |..P |.: none 0x0.4-0x2 (1.5)
|
||||
|00 01 02 03 04 05 06 07 08 09 0a 0b 0c 0d 0e 0f|0123456789abcdef|
|
||||
0x00|ff fb 50 c4 00 00 0a 2c 43 2e 55 94 80 01 80 93|..P....,C.U.....|.: none 0x0-0xcf.7 (208)
|
||||
* |until 0xcf.7 (end) (208) | |
|
||||
0
|
||||
208
|
||||
208
|
||||
|00 01 02 03 04 05 06 07 08 09 0a 0b 0c 0d 0e 0f|0123456789abcdef|
|
||||
0x00| 00 00 0a 2c 43 2e 55 94 80 01 80 93| ...,C.U.....|.: none 0x4-0x10.7 (13)
|
||||
0x10|6b |k |
|
||||
|00 01 02 03 04 05 06 07 08 09 0a 0b 0c 0d 0e 0f|0123456789abcdef|
|
||||
0x00|ff fb 50 c4 00 00 0a 2c 43 2e 55 94 80 01 80 93|..P....,C.U.....|.: none 0x0-0xcf.7 (208)
|
||||
* |until 0xcf.7 (end) (208) | |
|
||||
0
|
||||
1664
|
||||
1664
|
||||
|00 01 02 03 04 05 06 07 08 09 0a 0b 0c 0d 0e 0f|0123456789abcdef|
|
||||
0x0|ff fb 50 |..P |.: none 0x0.4-0x2 (1.5)
|
||||
|00 01 02 03 04 05 06 07 08 09 0a 0b 0c 0d 0e 0f|0123456789abcdef|
|
||||
0x00|ff fb 50 c4 00 00 0a 2c 43 2e 55 94 80 01 80 93|..P....,C.U.....|.: none 0x0-0xcf.7 (208)
|
||||
* |until 0xcf.7 (end) (208) | |
|
||||
0
|
||||
208
|
||||
208
|
||||
|00 01 02 03 04 05 06 07 08 09 0a 0b 0c 0d 0e 0f|0123456789abcdef|
|
||||
0x00| 00 00 0a 2c 43 2e 55 94 80 01 80 93| ...,C.U.....|.: none 0x4-0x10.7 (13)
|
||||
0x10|6b |k |
|
||||
mp3> .frames[1] | tobytes | ., .start, .stop, .size, .[4:17], (tobits, tobytes, tobitsrange, tobytesrange | ., .start, .stop, .size, .[4:17])
|
||||
|00 01 02 03 04 05 06 07 08 09 0a 0b 0c 0d 0e 0f|0123456789abcdef|
|
||||
0x00|ff fb 50 c4 00 00 0a 2c 43 2e 55 94 80 01 80 93|..P....,C.U.....|.: none 0x0-0xcf.7 (208)
|
||||
* |until 0xcf.7 (end) (208) | |
|
||||
0
|
||||
208
|
||||
208
|
||||
|00 01 02 03 04 05 06 07 08 09 0a 0b 0c 0d 0e 0f|0123456789abcdef|
|
||||
0x00| 00 00 0a 2c 43 2e 55 94 80 01 80 93| ...,C.U.....|.: none 0x4-0x10.7 (13)
|
||||
0x10|6b |k |
|
||||
|00 01 02 03 04 05 06 07 08 09 0a 0b 0c 0d 0e 0f|0123456789abcdef|
|
||||
0x00|ff fb 50 c4 00 00 0a 2c 43 2e 55 94 80 01 80 93|..P....,C.U.....|.: none 0x0-0xcf.7 (208)
|
||||
* |until 0xcf.7 (end) (208) | |
|
||||
0
|
||||
1664
|
||||
1664
|
||||
|00 01 02 03 04 05 06 07 08 09 0a 0b 0c 0d 0e 0f|0123456789abcdef|
|
||||
0x0|ff fb 50 |..P |.: none 0x0.4-0x2 (1.5)
|
||||
|00 01 02 03 04 05 06 07 08 09 0a 0b 0c 0d 0e 0f|0123456789abcdef|
|
||||
0x00|ff fb 50 c4 00 00 0a 2c 43 2e 55 94 80 01 80 93|..P....,C.U.....|.: none 0x0-0xcf.7 (208)
|
||||
* |until 0xcf.7 (end) (208) | |
|
||||
0
|
||||
208
|
||||
208
|
||||
|00 01 02 03 04 05 06 07 08 09 0a 0b 0c 0d 0e 0f|0123456789abcdef|
|
||||
0x00| 00 00 0a 2c 43 2e 55 94 80 01 80 93| ...,C.U.....|.: none 0x4-0x10.7 (13)
|
||||
0x10|6b |k |
|
||||
|00 01 02 03 04 05 06 07 08 09 0a 0b 0c 0d 0e 0f|0123456789abcdef|
|
||||
0x00|ff fb 50 c4 00 00 0a 2c 43 2e 55 94 80 01 80 93|..P....,C.U.....|.: none 0x0-0xcf.7 (208)
|
||||
* |until 0xcf.7 (end) (208) | |
|
||||
0
|
||||
1664
|
||||
1664
|
||||
|00 01 02 03 04 05 06 07 08 09 0a 0b 0c 0d 0e 0f|0123456789abcdef|
|
||||
0x0|ff fb 50 |..P |.: none 0x0.4-0x2 (1.5)
|
||||
|00 01 02 03 04 05 06 07 08 09 0a 0b 0c 0d 0e 0f|0123456789abcdef|
|
||||
0x00|ff fb 50 c4 00 00 0a 2c 43 2e 55 94 80 01 80 93|..P....,C.U.....|.: none 0x0-0xcf.7 (208)
|
||||
* |until 0xcf.7 (end) (208) | |
|
||||
0
|
||||
208
|
||||
208
|
||||
|00 01 02 03 04 05 06 07 08 09 0a 0b 0c 0d 0e 0f|0123456789abcdef|
|
||||
0x00| 00 00 0a 2c 43 2e 55 94 80 01 80 93| ...,C.U.....|.: none 0x4-0x10.7 (13)
|
||||
0x10|6b |k |
|
||||
mp3> .frames[1] | tobitsrange | ., .start, .stop, .size, .[4:17], (tobits, tobytes, tobitsrange, tobytesrange | ., .start, .stop, .size, .[4:17])
|
||||
|00 01 02 03 04 05 06 07 08 09 0a 0b 0c 0d 0e 0f|0123456789abcdef|
|
||||
0x0e0| ff fb 50 c4 00 00 0a 2c 43 2e 55 94 80| ..P....,C.U..|.: none 0xe3-0x1b2.7 (208)
|
||||
0x0f0|01 80 93 6b 27 30 80 00 07 aa c3 8e 33 85 d3 64|...k'0......3..d|
|
||||
* |until 0x1b2.7 (208) | |
|
||||
1816
|
||||
3480
|
||||
1664
|
||||
|00 01 02 03 04 05 06 07 08 09 0a 0b 0c 0d 0e 0f|0123456789abcdef|
|
||||
0xe0| ff fb 50 | ..P |.: none 0xe3.4-0xe5 (1.5)
|
||||
|00 01 02 03 04 05 06 07 08 09 0a 0b 0c 0d 0e 0f|0123456789abcdef|
|
||||
0x00|ff fb 50 c4 00 00 0a 2c 43 2e 55 94 80 01 80 93|..P....,C.U.....|.: none 0x0-0xcf.7 (208)
|
||||
* |until 0xcf.7 (end) (208) | |
|
||||
0
|
||||
1664
|
||||
1664
|
||||
|00 01 02 03 04 05 06 07 08 09 0a 0b 0c 0d 0e 0f|0123456789abcdef|
|
||||
0x0|ff fb 50 |..P |.: none 0x0.4-0x2 (1.5)
|
||||
|00 01 02 03 04 05 06 07 08 09 0a 0b 0c 0d 0e 0f|0123456789abcdef|
|
||||
0x00|ff fb 50 c4 00 00 0a 2c 43 2e 55 94 80 01 80 93|..P....,C.U.....|.: none 0x0-0xcf.7 (208)
|
||||
* |until 0xcf.7 (end) (208) | |
|
||||
0
|
||||
208
|
||||
208
|
||||
|00 01 02 03 04 05 06 07 08 09 0a 0b 0c 0d 0e 0f|0123456789abcdef|
|
||||
0x00| 00 00 0a 2c 43 2e 55 94 80 01 80 93| ...,C.U.....|.: none 0x4-0x10.7 (13)
|
||||
0x10|6b |k |
|
||||
|00 01 02 03 04 05 06 07 08 09 0a 0b 0c 0d 0e 0f|0123456789abcdef|
|
||||
0x0e0| ff fb 50 c4 00 00 0a 2c 43 2e 55 94 80| ..P....,C.U..|.: none 0xe3-0x1b2.7 (208)
|
||||
0x0f0|01 80 93 6b 27 30 80 00 07 aa c3 8e 33 85 d3 64|...k'0......3..d|
|
||||
* |until 0x1b2.7 (208) | |
|
||||
1816
|
||||
3480
|
||||
1664
|
||||
|00 01 02 03 04 05 06 07 08 09 0a 0b 0c 0d 0e 0f|0123456789abcdef|
|
||||
0xe0| ff fb 50 | ..P |.: none 0xe3.4-0xe5 (1.5)
|
||||
|00 01 02 03 04 05 06 07 08 09 0a 0b 0c 0d 0e 0f|0123456789abcdef|
|
||||
0x0e0| ff fb 50 c4 00 00 0a 2c 43 2e 55 94 80| ..P....,C.U..|.: none 0xe3-0x1b2.7 (208)
|
||||
0x0f0|01 80 93 6b 27 30 80 00 07 aa c3 8e 33 85 d3 64|...k'0......3..d|
|
||||
* |until 0x1b2.7 (208) | |
|
||||
227
|
||||
435
|
||||
208
|
||||
|00 01 02 03 04 05 06 07 08 09 0a 0b 0c 0d 0e 0f|0123456789abcdef|
|
||||
0xe0| 00 00 0a 2c 43 2e 55 94 80| ...,C.U..|.: none 0xe7-0xf3.7 (13)
|
||||
0xf0|01 80 93 6b |...k |
|
||||
mp3> .frames[1] | tobytesrange | ., .start, .stop, .size, .[4:17], (tobits, tobytes, tobitsrange, tobytesrange | ., .start, .stop, .size, .[4:17])
|
||||
|00 01 02 03 04 05 06 07 08 09 0a 0b 0c 0d 0e 0f|0123456789abcdef|
|
||||
0x0e0| ff fb 50 c4 00 00 0a 2c 43 2e 55 94 80| ..P....,C.U..|.: none 0xe3-0x1b2.7 (208)
|
||||
0x0f0|01 80 93 6b 27 30 80 00 07 aa c3 8e 33 85 d3 64|...k'0......3..d|
|
||||
* |until 0x1b2.7 (208) | |
|
||||
227
|
||||
435
|
||||
208
|
||||
|00 01 02 03 04 05 06 07 08 09 0a 0b 0c 0d 0e 0f|0123456789abcdef|
|
||||
0xe0| 00 00 0a 2c 43 2e 55 94 80| ...,C.U..|.: none 0xe7-0xf3.7 (13)
|
||||
0xf0|01 80 93 6b |...k |
|
||||
|00 01 02 03 04 05 06 07 08 09 0a 0b 0c 0d 0e 0f|0123456789abcdef|
|
||||
0x00|ff fb 50 c4 00 00 0a 2c 43 2e 55 94 80 01 80 93|..P....,C.U.....|.: none 0x0-0xcf.7 (208)
|
||||
* |until 0xcf.7 (end) (208) | |
|
||||
0
|
||||
1664
|
||||
1664
|
||||
|00 01 02 03 04 05 06 07 08 09 0a 0b 0c 0d 0e 0f|0123456789abcdef|
|
||||
0x0|ff fb 50 |..P |.: none 0x0.4-0x2 (1.5)
|
||||
|00 01 02 03 04 05 06 07 08 09 0a 0b 0c 0d 0e 0f|0123456789abcdef|
|
||||
0x00|ff fb 50 c4 00 00 0a 2c 43 2e 55 94 80 01 80 93|..P....,C.U.....|.: none 0x0-0xcf.7 (208)
|
||||
* |until 0xcf.7 (end) (208) | |
|
||||
0
|
||||
208
|
||||
208
|
||||
|00 01 02 03 04 05 06 07 08 09 0a 0b 0c 0d 0e 0f|0123456789abcdef|
|
||||
0x00| 00 00 0a 2c 43 2e 55 94 80 01 80 93| ...,C.U.....|.: none 0x4-0x10.7 (13)
|
||||
0x10|6b |k |
|
||||
|00 01 02 03 04 05 06 07 08 09 0a 0b 0c 0d 0e 0f|0123456789abcdef|
|
||||
0x0e0| ff fb 50 c4 00 00 0a 2c 43 2e 55 94 80| ..P....,C.U..|.: none 0xe3-0x1b2.7 (208)
|
||||
0x0f0|01 80 93 6b 27 30 80 00 07 aa c3 8e 33 85 d3 64|...k'0......3..d|
|
||||
* |until 0x1b2.7 (208) | |
|
||||
1816
|
||||
3480
|
||||
1664
|
||||
|00 01 02 03 04 05 06 07 08 09 0a 0b 0c 0d 0e 0f|0123456789abcdef|
|
||||
0xe0| ff fb 50 | ..P |.: none 0xe3.4-0xe5 (1.5)
|
||||
|00 01 02 03 04 05 06 07 08 09 0a 0b 0c 0d 0e 0f|0123456789abcdef|
|
||||
0x0e0| ff fb 50 c4 00 00 0a 2c 43 2e 55 94 80| ..P....,C.U..|.: none 0xe3-0x1b2.7 (208)
|
||||
0x0f0|01 80 93 6b 27 30 80 00 07 aa c3 8e 33 85 d3 64|...k'0......3..d|
|
||||
* |until 0x1b2.7 (208) | |
|
||||
227
|
||||
435
|
||||
208
|
||||
|00 01 02 03 04 05 06 07 08 09 0a 0b 0c 0d 0e 0f|0123456789abcdef|
|
||||
0xe0| 00 00 0a 2c 43 2e 55 94 80| ...,C.U..|.: none 0xe7-0xf3.7 (13)
|
||||
0xf0|01 80 93 6b |...k |
|
||||
mp3> ^D
|
||||
|
Loading…
Reference in New Issue
Block a user