Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merge from upstream #8

Merged
merged 12 commits into from
Aug 31, 2018
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 0 additions & 2 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -20,8 +20,6 @@ a.out
*.class
*.pyxbldc
*.vcd
lane.cpp
loc*.cpp
config.json
clcache

Expand Down
6 changes: 3 additions & 3 deletions CONTRIBUTING.md
Original file line number Diff line number Diff line change
Expand Up @@ -8,11 +8,11 @@ Most open source development activity is coordinated through our [slack](https:/

* Join our slack [slack.comma.ai](https://slack.comma.ai)
* Make sure you have a [GitHub account](https://github.com/signup/free)
* Fork the repository on GitHub
* Fork [our repositories](https://github.com/commaai) on GitHub

## Car Ports (openpilot)

We've released a guide for porting to Toyota cars [here](https://medium.com/@comma_ai/openpilot-port-guide-for-toyota-models-e5467f4b5fe6)
We've released a [Model Port guide](https://medium.com/@comma_ai/openpilot-port-guide-for-toyota-models-e5467f4b5fe6) for porting to Toyota/Lexus models.

If you port openpilot to a substantially new car, you might be eligible for a bounty. See our bounties at [comma.ai/bounties.html](https://comma.ai/bounties.html)
If you port openpilot to a substantially new car brand, see this more generic [Brand Port guide](https://medium.com/@comma_ai/how-to-write-a-car-port-for-openpilot-7ce0785eda84). You might also be eligible for a bounty. See our bounties at [comma.ai/bounties.html](https://comma.ai/bounties.html)

12 changes: 7 additions & 5 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -53,14 +53,16 @@ Supported Cars
| Honda | Civic 2017 | Honda Sensing | Yes | Yes | 0mph | 12mph |
| Honda | Civic 2017 *(Hatch)* | Honda Sensing | Yes | Stock | 0mph | 12mph |
| Honda | Civic 2018 | Honda Sensing | Yes | Yes | 0mph | 12mph |
| Honda | CR-V 2015 | Honda Sensing | Yes | Yes | 25mph<sup>1</sup>| 12mph |
| Honda | CR-V 2016 | Honda Sensing | Yes | Yes | 25mph<sup>1</sup>| 12mph |
| Honda | Civic 2018 *(Hatch)* | Honda Sensing | Yes | Stock | 0mph | 12mph |
| Honda | CR-V 2015 | Touring | Yes | Yes | 25mph<sup>1</sup>| 12mph |
| Honda | CR-V 2016 | Touring | Yes | Yes | 25mph<sup>1</sup>| 12mph |
| Honda | CR-V 2017 | Honda Sensing | Yes | Stock | 0mph | 12mph |
| Honda | CR-V 2018 | Honda Sensing | Yes | Stock | 0mph | 12mph |
| Honda | Odyssey 2017 | Honda Sensing | Yes | Yes | 25mph<sup>1</sup>| 12mph |
| Honda | Odyssey 2018 | Honda Sensing | Yes | Yes | 25mph<sup>1</sup>| 12mph |
| Honda | Odyssey 2017 | Honda Sensing | Yes | Yes | 25mph<sup>1</sup>| 0mph |
| Honda | Odyssey 2018 | Honda Sensing | Yes | Yes | 25mph<sup>1</sup>| 0mph |
| Honda | Pilot 2017 | Honda Sensing | Yes | Yes | 25mph<sup>1</sup>| 12mph |
| Honda | Pilot 2018 | Honda Sensing | Yes | Yes | 25mph<sup>1</sup>| 12mph |
| Honda | Pilot 2019 | All | Yes | Yes | 25mph<sup>1</sup>| 12mph |
| Honda | Ridgeline 2017 | Honda Sensing | Yes | Yes | 25mph<sup>1</sup>| 12mph |
| Honda | Ridgeline 2018 | Honda Sensing | Yes | Yes | 25mph<sup>1</sup>| 12mph |
| Lexus | RX Hybrid 2017 | All | Yes | Yes<sup>2</sup>| 0mph | 0mph |
Expand Down Expand Up @@ -96,7 +98,7 @@ Community Maintained Cars

[[Honda Fit Pull Request]](https://github.com/commaai/openpilot/pull/266).

Community Maintained Cars are not confirmed by comma.ai to meet our safety model. Be extra cautious using them.
Community Maintained Cars are not confirmed by comma.ai to meet our [safety model](https://github.com/commaai/openpilot/blob/devel/SAFETY.md). Be extra cautious using them.

In Progress Cars
------
Expand Down
8 changes: 8 additions & 0 deletions RELEASES.md
Original file line number Diff line number Diff line change
@@ -1,3 +1,11 @@
Version 0.5.2 (2018-08-16)
========================
* New calibration: more accurate, a lot faster, open source!
* Enable orbd
* Add little endian support to CAN packer
* Fix fingerprint for Honda Accord 1.5T
* Improve driver monitoring model

Version 0.5.1 (2018-08-01)
========================
* Fix radar error on Civic sedan 2018
Expand Down
1 change: 1 addition & 0 deletions cereal/car.capnp
Original file line number Diff line number Diff line change
Expand Up @@ -309,6 +309,7 @@ struct CarParams {
cadillac @7;
hyundai @8;
chrysler @9;
tesla @10;
}

# things about the car in the manual
Expand Down
5 changes: 4 additions & 1 deletion cereal/log.capnp
Original file line number Diff line number Diff line change
Expand Up @@ -331,13 +331,16 @@ struct Live20Data {
}

struct LiveCalibrationData {
# deprecated
warpMatrix @0 :List(Float32);
# camera_frame_from_model_frame
warpMatrix2 @5 :List(Float32);
calStatus @1 :Int8;
calCycle @2 :Int32;
calPerc @3 :Int8;

# Maps car space to normalized image space.
# view_frame_from_road_frame
# ui's is inversed needs new
extrinsicMatrix @4 :List(Float32);
}

Expand Down
30 changes: 29 additions & 1 deletion common/dbc.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@
import bitstring
import sys
import numbers
from collections import namedtuple
from collections import namedtuple, defaultdict

def int_or_float(s):
# return number, trying to maintain int format
Expand All @@ -28,6 +28,7 @@ def __init__(self, fn):
bo_regexp = re.compile(r"^BO\_ (\w+) (\w+) *: (\w+) (\w+)")
sg_regexp = re.compile(r"^SG\_ (\w+) : (\d+)\|(\d+)@(\d+)([\+|\-]) \(([0-9.+\-eE]+),([0-9.+\-eE]+)\) \[([0-9.+\-eE]+)\|([0-9.+\-eE]+)\] \"(.*)\" (.*)")
sgm_regexp = re.compile(r"^SG\_ (\w+) (\w+) *: (\d+)\|(\d+)@(\d+)([\+|\-]) \(([0-9.+\-eE]+),([0-9.+\-eE]+)\) \[([0-9.+\-eE]+)\|([0-9.+\-eE]+)\] \"(.*)\" (.*)")
val_regexp = re.compile(r"VAL\_ (\w+) (\w+) (\s*[-+]?[0-9]+\s+\".+?\"[^;]*)")

# A dictionary which maps message ids to tuples ((name, size), signals).
# name is the ASCII name of the message.
Expand All @@ -36,6 +37,9 @@ def __init__(self, fn):
# signals is a list of DBCSignal in order of increasing start_bit.
self.msgs = {}

# A dictionary which maps message ids to a list of tuples (signal name, definition value pairs)
self.def_vals = defaultdict(list)

# lookup to bit reverse each byte
self.bits_index = [(i & ~0b111) + ((-i-1) & 0b111) for i in xrange(64)]

Expand Down Expand Up @@ -81,6 +85,30 @@ def __init__(self, fn):
DBCSignal(sgname, start_bit, signal_size, is_little_endian,
is_signed, factor, offset, tmin, tmax, units))

if l.startswith("VAL_ "):
# new signal value/definition
dat = val_regexp.match(l)

if dat is None:
print "bad VAL", l
ids = int(dat.group(1), 0) # could be hex
sgname = dat.group(2)
defvals = dat.group(3)

defvals = defvals.replace("?","\?") #escape sequence in C++
defvals = defvals.split('"')[:-1]

defs = defvals[1::2]
#cleanup, convert to UPPER_CASE_WITH_UNDERSCORES
for i,d in enumerate(defs):
d = defs[i].strip().upper()
defs[i] = d.replace(" ","_")

defvals[1::2] = defs
defvals = '"'+"".join(str(i) for i in defvals)+'"'

self.def_vals[ids].append((sgname, defvals))

for msg in self.msgs.viewvalues():
msg[1].sort(key=lambda x: x.start_bit)

Expand Down
42 changes: 42 additions & 0 deletions common/ffi_wrapper.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,42 @@
import os
import sys
import fcntl
import hashlib
from cffi import FFI

TMPDIR = "/tmp/ccache"

def ffi_wrap(name, c_code, c_header, tmpdir=TMPDIR):
cache = name + "_" + hashlib.sha1(c_code).hexdigest()
try:
os.mkdir(tmpdir)
except OSError:
pass

fd = os.open(tmpdir, 0)
fcntl.flock(fd, fcntl.LOCK_EX)
try:
sys.path.append(tmpdir)
try:
mod = __import__(cache)
except Exception:
print "cache miss", cache
compile_code(cache, c_code, c_header, tmpdir)
mod = __import__(cache)
finally:
os.close(fd)

return mod.ffi, mod.lib

def compile_code(name, c_code, c_header, directory):
ffibuilder = FFI()
ffibuilder.set_source(name, c_code, source_extension='.cpp')
ffibuilder.cdef(c_header)
os.environ['OPT'] = "-fwrapv -O2 -DNDEBUG -std=c++11"
os.environ['CFLAGS'] = ""
ffibuilder.compile(verbose=True, debug=False, tmpdir=directory)

def wrap_compiled(name, directory):
sys.path.append(directory)
mod = __import__(name)
return mod.ffi, mod.lib
58 changes: 40 additions & 18 deletions common/params.py
Original file line number Diff line number Diff line change
Expand Up @@ -66,9 +66,6 @@ class UnknownKeyName(Exception):
# written: visiond
# read: visiond, controlsd
"CalibrationParams": TxType.PERSISTENT,
# written: visiond
# read: visiond, ui
"CloudCalibration": TxType.PERSISTENT,
# written: controlsd
# read: radard
"CarParams": TxType.CLEAR_ON_CAR_START,
Expand Down Expand Up @@ -266,23 +263,50 @@ def __exit__(self, type, value, traceback):
self._lock = None


def read_db(params_path, key):
path = "%s/d/%s" % (params_path, key)
try:
with open(path, "rb") as f:
return f.read()
except IOError:
return None

class JSDB(object):
def __init__(self, fn):
self._fn = fn
def write_db(params_path, key, value):
prev_umask = os.umask(0)
lock = FileLock(params_path+"/.lock", True)
lock.acquire()

def begin(self, write=False):
if write:
return DBWriter(self._fn)
else:
return DBReader(self._fn)
try:
tmp_path = tempfile.mktemp(prefix=".tmp", dir=params_path)
with open(tmp_path, "wb") as f:
f.write(value)
f.flush()
os.fsync(f.fileno())

path = "%s/d/%s" % (params_path, key)
os.rename(tmp_path, path)
fsync_dir(os.path.dirname(path))
finally:
os.umask(prev_umask)
lock.release()

class Params(object):
def __init__(self, db='/data/params'):
self.env = JSDB(db)
self.db = db

# create the database if it doesn't exist...
if not os.path.exists(self.db+"/d"):
with self.transaction(write=True):
pass

def transaction(self, write=False):
if write:
return DBWriter(self.db)
else:
return DBReader(self.db)

def _clear_keys_with_type(self, tx_type):
with self.env.begin(write=True) as txn:
with self.transaction(write=True) as txn:
for key in keys:
if keys[key] == tx_type:
txn.delete(key)
Expand All @@ -294,16 +318,15 @@ def car_start(self):
self._clear_keys_with_type(TxType.CLEAR_ON_CAR_START)

def delete(self, key):
with self.env.begin(write=True) as txn:
with self.transaction(write=True) as txn:
txn.delete(key)

def get(self, key, block=False):
if key not in keys:
raise UnknownKeyName(key)

while 1:
with self.env.begin() as txn:
ret = txn.get(key)
ret = read_db(self.db, key)
if not block or ret is not None:
break
# is polling really the best we can do?
Expand All @@ -314,8 +337,7 @@ def put(self, key, dat):
if key not in keys:
raise UnknownKeyName(key)

with self.env.begin(write=True) as txn:
txn.put(key, dat)
write_db(self.db, key, dat)

if __name__ == "__main__":
params = Params()
Expand Down
Loading