Research
Security News
Malicious npm Packages Inject SSH Backdoors via Typosquatted Libraries
Socket’s threat research team has detected six malicious npm packages typosquatting popular libraries to insert SSH backdoors.
@keiser/echip-webusb
Advanced tools
This library handles communication with the Chip USB reader using WebUSB.
Required Hardware: USB to 1-Wire/iButton Adapter (DS9490)
Required Drivers: 1-Wire/iButton Drivers for Windows
Install with NPM: npm install @keiser/echip-webusb
Import singleton instance from module using preferred module loading technique.
import ChipReaderWatcher from '@keiser/echip-webusb'
if (ChipReaderWatcher.isConnected) {
console.log('Chip Reader Connected 😄')
}
The ChipReaderWatcher
handles permissions and USB connection events. On first load, the browser will not have provided a grant to the site to access the USB device, so the ChipReaderWatcher.start()
method must be called by an event that originates from a user action. This may only be required once on the first visit to the site, or it may be required each time the site is loaded based on browser vendors preferred implementation.
connectButton.addEventListener('click', async () => {
try {
await ChipReaderWatcher.start()
} catch (error) {
console.error(error.message)
}
})
Once the ChipReaderWatcher.start()
method has been called the class will prompt the browser for permission and begin watching for devices matching the Chip Readers device signature. To be alerted when a device is found, pass a function to the ChipReaderWatcher.onConnect()
method.
ChipReaderWatcher.onConnect((chipReader) => {
console.log('Chip Reader Connected 😄')
})
The ChipReaderWatcher.onConnect()
will pass in a ChipReader
object which is the object bound to the physical device connected. This library is capable of handling multiple Chip Reader devices simultaneously, so the onConnect()
method has potential for returning multiple ChipReader
devices over the course of the application's life.
chipReader.onDisconnect(() => {
console.log('Chip Reader Disconnected 😞')
})
The ChipReader
object has an onDisconnect()
method which will alert when the Chip Reader has been disconnected for some reason. Once a ChipReader
object has been disconnected, it is disposed and cannot be used again. The next time the device is connected, a new ChipReader
object will be returned.
chipReader.onChipDetect(async (chip) => {
console.log('Chip Connected: ' + chip.id)
console.log(await chip.getData())
})
The ChipReader
object also has an onChipDetect()
method which will alert when a valid chip has been placed into the reader. The event passes in a Chip
object that can be used to interact with the chip data directly. Just like the ChipReaderWatcher.onConnect()
method, the ChipReader.onChipDetect()
method can be called multiple times for multiple chips all being handled concurrently. Once a chip is disconnected, the Chip
object is disposed and cannot be reused.
Full example usage:
import ChipReaderWatcher from '@keiser/echip-webusb'
document.addEventListener('DOMContentLoaded', event => {
const connectButton = document.querySelector('#connect') as HTMLInputElement
if (connectButton) {
connectButton.addEventListener('click', async () => {
try {
await ChipReaderWatcher.start()
} catch (error) {
console.error(error.message)
}
})
}
ChipReaderWatcher.onConnect((chipReader) => {
console.log('Chip Reader Connected 😄')
chipReader.onChipDetect(async (chip) => {
console.log('Chip Connected: ' + chip.id)
chip.onData(data => console.log(data))
})
chipReader.onDisconnect(() => {
console.log('Chip Reader Disconnected 😞')
})
})
})
The ChipReaderWatcher
is a singleton class which handles the USB device monitoring and permissions handling. There can be only one ChipReaderWatcher
instance created within a window
scope, so the library instantiates the class during import and preserves a single instance for all imports.
Name | Usage |
---|---|
isConnected: boolean | Indicates whether a Chip Reader device is connected |
Name | Usage |
---|---|
onConnect(Listener<ChipReader>): Disposable | Adds an event listener for when a Chip Reader device is connected. Callback method will be passed the new ChipReader instance for the connected device. |
start(): Promise<void> | Initializes the watcher by first requesting permissions and then doing a hardware search. This method must be triggered by a user action such as a click event or the permission request will be denied. |
stop(): Promise<void> | Closes all active connections. |
The ChipReader
instance is passed into the onConnect
callback function and is the interface to the connected Chip Reader device.
Name | Usage |
---|---|
claimed: Promise<boolean> | Promise indicating if the USB device interface has been claimed. |
disposed: boolean | Indicates if the device connection has been severed and the class instance disposed. |
Name | Usage |
---|---|
onChipDetect(Listener<Chip>): Disposable | Adds an event listener for when a chip is connected to the Chip Reader device. Callback method will be passed the new Chip instance for the connected chip. |
onDisconnect(Listener<null>): Disposable | Adds an event listener for when this Chip Reader device becomes disconnected. The instance will be disposed following this event. |
The BaseChip
instance is passed into the onChipDetect
callback function and is the interface to the connected chip device. There are several different extensions to the base BaseChip
object that can identified by doing a instanceOf
check or looking at the type
property.
Name | Usage |
---|---|
disposed: boolean | Indicates if the eChip connection has been severed and the class instance disposed. |
data: ChipObject | Generic object with the current data from the chip. |
id: string | UUID string of the eChip. |
type: ChipType | ChipType enum value corresponding to the type of chip. |
Name | Usage |
---|---|
destroy(): void | Called to disconnect the eChip device. |
onDisconnect(Listener<null>): Disposable | Adds an event listener for when this chip becomes disconnected. The instance will be disposed following this event. |
onData(Listener<ChipObject>): Disposable | Adds an event listener for when the chip data has changed. |
The TZChip
and RTCChip
are class extensions on the BaseChip
class. They add no additional properties or methods, but allow the identification of chip type and will perform chip set operations automatically when detected. An event issued on the onData
event indicates that the chips data has been successfully updated.
The DataChip
class extension on the BaseChip
class adds additional properties and methods specific to the data chip.
Name | Usage |
---|---|
clearData(): Promise<void> | Method clears the data on the chip and resolve the promise on successful write. An onData event will be issues for the blank chip data. |
setData({string: MachineObject}): Promise<void> | Method sets the data on the chip according to the data passed into the method. The method accepts an object with string keys corresponding to the machine's 4-digit model number with the MachineObject as the value of the property. Method resolve the promise on successful write. An onData event will be issues for the freshly written chip data. |
interface ChipObject {
type: ChipType
}
interface DataChipObject {
type: ChipType
machineData: {[index: string]: MachineObject}
rawData: Uint8Array[]
validStructure: boolean
}
interface MachineObject {
position: MachinePosition
sets: MachineSet[]
}
interface MachinePosition {
chest: number | null
rom2: number | null
rom1: number | null
seat: number | null
}
interface MachineSet {
version: string
serial: string
time: string
resistance: number
precision: Precision
units: ForceUnit
repetitions: number
peak: number | null
work: number | null
distance: number | null
chest: number | null
rom2: number | null
rom1: number | null
seat: number | null
test: MachineTest | null
}
interface MachineTest {
type: TestType
high: MachineTestResult | null
low: MachineTestResult | null
}
interface MachineTestResult {
power: number
velocity: number
force: number
position: number
}
enum Precision {
dec = 'dec',
int = 'int'
}
enum ForceUnit {
lb = 'lb',
kg = 'kg',
ne = 'ne',
er = 'er'
}
enum TestType {
power6r = 'power6r',
a4206r = 'a4206r',
a42010r = 'a42010r'
}
enum ChipType {
dataChip = 12,
rtcChip = 36,
tzChip = 45,
unknown = 0
}
Maxim Integrated 1-Wire USB Android notes
Maxim Integrated 1-Wire USB Android project
Copyright Keiser Corporation under the MIT license.
FAQs
Keiser Air eChip WebUSB Library
The npm package @keiser/echip-webusb receives a total of 2 weekly downloads. As such, @keiser/echip-webusb popularity was classified as not popular.
We found that @keiser/echip-webusb demonstrated a not healthy version release cadence and project activity because the last version was released a year ago. It has 2 open source maintainers collaborating on the project.
Did you know?
Socket for GitHub automatically highlights issues in each pull request and monitors the health of all your open source dependencies. Discover the contents of your packages and block harmful activity before you install or update your dependencies.
Research
Security News
Socket’s threat research team has detected six malicious npm packages typosquatting popular libraries to insert SSH backdoors.
Security News
MITRE's 2024 CWE Top 25 highlights critical software vulnerabilities like XSS, SQL Injection, and CSRF, reflecting shifts due to a refined ranking methodology.
Security News
In this segment of the Risky Business podcast, Feross Aboukhadijeh and Patrick Gray discuss the challenges of tracking malware discovered in open source softare.