RiftCat / vridge-api

VRidge API is a way to read and write all head and motion controller tracking data used by VRidge.
https://riftcat.com/vridge
MIT License
53 stars 15 forks source link

VRidge - Fatal error when sending Quanternion Rotation + Position #25

Closed mungewell closed 4 years ago

mungewell commented 4 years ago

I am playing with VRidge API sending rotations/positions computed from PSVR accel/gyros, but am getting a fatal error when sending the rotation as a Quanternion. There is quite a bit of history in Bug #17.

Error message is, and log file attached. vridge_fatal_error VRidge.log

If I send rotations as angles then system works as expected. Has something changed within the protcol? https://github.com/RiftCat/vridge-api/wiki/Head-Tracking-API#writing-tracking-data

Back around the end of 2018 both methods worked (to some degree). My code is

    if options.angle:
        (y,p,r) = ahrs.quaternion.yaw_pitch_roll
        data = tuple((p,y,r)) + position
        output = anglesposition.build(dict(data=list(data)))
    else:
        # Send as Quaternion (note: VRidge params switched)
        (w,x,y,z) = ahrs.quaternion.elements
        data = tuple((y,z,x,w)) + position

        output = quaternionposition.build(dict(data=list(data)))

    # Update position in VRidge
    headset.send(output)
    answer = headset.recv()
mungewell commented 4 years ago

Riftcat is reporting version '2.6.3'.

Is it possible to back data to what was current around Jan 2019, to confirm that it really did work? (looks like that would have been 2.2.7 or 2.2.7.0)

balukin commented 4 years ago

Could you capture the faulting data right before you send it and paste it here? TaskType integer and Data byte array should suffice.

I'm gonna reproduce it on our side with v1 API. The interface is a bit old but it should still be working, if I recall correctly.

mungewell commented 4 years ago

Here you go:

C:\Users\simon\Downloads\pyPSVR-trezor\example4_vridge_sensors>"c:\Program Files\Python36\python.exe" vridge_psvr.py -c -D
Connecting to tcp://192.168.0.116:38219
{'Endpoints': [{'Name': 'HeadTracking', 'InUseBy': None, 'ProtocolVersion': 3, 'Code': 0}, {'Name': 'Controller', 'InUseBy': None, 'ProtocolVersion': 3, 'Code': 0}, {'Name': 'Broadcast', 'InUseBy': None, 'ProtocolVersion': 3, 'Code': 0}], 'ProtocolVersion': 3, 'Code': 0}
{'ProtocolVersion': 3, 'Code': 0, 'EndpointAddress': 'tcp://localhost:38320', 'TimeoutSec': 15}
Calibrating sensor - keep PSVR stationary 5s
Gcomp: [ 6.77252425 -7.6583585   0.50357613]
Position:  (0.0, 1.2, 0.0)
Euler:  (-9.3558029196339266e-06, 0.00020948748323162524, 1.4264220935096475e-05)
Quat:   [  9.99999994e-01   7.13162045e-06   1.04743775e-04  -4.67715439e-06]

00000000: 02 00 00 00 04 00 00 00  18 00 00 00 E3 A9 DB 38  ...............8
00000010: 73 F0 9C B6 27 4C EF 36  00 00 80 3F 00 00 00 00  s...'L.6...?....
00000020: 9A 99 99 3F 00 00 00 00  00 00 00 00 00 00 00 00  ...?............
00000030: 00 00 00 00 00 00 00 00  00 00 00 00 00 00 00 00  ................
00000040: 00 00 00 00 00 00 00 00  00 00 00 00              ............
None

Note the parameter switching within the Quanterion (which seemed to work before)

# Send as Quaternion (note: VRidge params switched)
(w,x,y,z) = ahrs.quaternion.elements
data = tuple((y,z,x,w)) + position
balukin commented 4 years ago

I will attempt to reproduce it early next week.

balukin commented 4 years ago

I didn't plug the data into vridge api v1 yet but it seems that there's an error in data length field. Breaking it down, the packet is formatted as:

[02 00 00 00]: Version = 2
[04 00 00 00]: Task = 2 (interpret data as quaternion followed by position)
[18 00 00 00]: Data length = 24
[E3 A9 DB 38 73 F0 9C B6  27 4C EF 36 00 00 80 3F 
 00 00 00 00 9A 99 99 3F  00 00 00 00 00 00 00 00 
 00 00 00 00 00 00 00 00  00 00 00 00 00 00 00 00 
 00 00 00 00 00 00 00 00  00 00 00 00 00 00 00 00]: Data itself

Quaternion + position needs a total of 7 floats (4 for quaternion, 3 for position), so 7*4=28 bytes total. API server sees 24 as data length and allocates only 24 bytes which later fails because later 7 floats are expected to be read from the buffer which results in System.ArgumentException: Offset and length were out of bounds

Internal tracking code was changed quite a few times and there wasn't an intermediate buffer before which would conceal the incorrect data length parameter.

balukin commented 4 years ago

Closing due to lack of activity. Please reopen if the issue happens with correct Data length field

mungewell commented 4 years ago

Been way to busy this year to get much done, but yes you are correct. Bug was caused by sending the wrong length value in the packet, fixed this and it works again.