/** * DesfireFile.kt * * Copyright (C) 2011 Eric Butler * Copyright (C) 2019 * * Authors: * Eric Butler * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ package com.codebutler.farebot.card.desfire import android.os.Parcel import android.os.Parcelable import com.codebutler.farebot.card.desfire.DesfireFileSettings.RecordDesfireFileSettings import org.apache.commons.lang3.ArrayUtils open class DesfireFile private constructor(val id: Int, private val fileSettings: DesfireFileSettings?, val data: ByteArray) : Parcelable { override fun writeToParcel(parcel: Parcel, flags: Int) { parcel.writeInt(id) if (this is InvalidDesfireFile) { parcel.writeInt(1) parcel.writeString(this.errorMessage) } else { parcel.writeInt(0) parcel.writeParcelable(fileSettings, 0) parcel.writeInt(data.size) parcel.writeByteArray(data) } } override fun describeContents(): Int { return 0 } class RecordDesfireFile(fileId: Int, fileSettings: DesfireFileSettings, fileData: ByteArray) : DesfireFile(fileId, fileSettings, fileData) { private val records: Array init { val settings = fileSettings as RecordDesfireFileSettings val records = arrayOfNulls(settings.curRecords) for (i in 0 until settings.curRecords) { val offset = settings.recordSize * i records[i] = DesfireRecord(ArrayUtils.subarray(data, offset, offset + settings.recordSize)) } this.records = records } } class InvalidDesfireFile(fileId: Int, val errorMessage: String?) : DesfireFile(fileId, null, ByteArray(0)) companion object { fun create(fileId: Int, fileSettings: DesfireFileSettings, fileData: ByteArray): DesfireFile { return (fileSettings as? RecordDesfireFileSettings)?.let { RecordDesfireFile(fileId, it, fileData) } ?: DesfireFile(fileId, fileSettings, fileData) } @Suppress("unused") @JvmField val CREATOR: Parcelable.Creator = object : Parcelable.Creator { override fun createFromParcel(source: Parcel): DesfireFile { val fileId = source.readInt() val isError = source.readInt() == 1 return if (!isError) { val fileSettings = source.readParcelable(DesfireFileSettings::class.java.classLoader) as DesfireFileSettings val dataLength = source.readInt() val fileData = ByteArray(dataLength) source.readByteArray(fileData) create(fileId, fileSettings, fileData) } else { InvalidDesfireFile(fileId, source.readString()) } } override fun newArray(size: Int): Array { return arrayOfNulls(size) } } } }