mirror of
https://github.com/google/flatbuffers.git
synced 2026-06-19 21:25:42 +00:00
[swift] Implements union strings (#6589)
This commit is contained in:
@@ -28,7 +28,7 @@ public struct FlatBufferBuilder {
|
||||
/// A check if the buffer is being written into by a different table
|
||||
private var isNested = false
|
||||
/// Dictonary that stores a map of all the strings that were written to the buffer
|
||||
private var stringOffsetMap: [String: Offset<String>] = [:]
|
||||
private var stringOffsetMap: [String: Offset] = [:]
|
||||
/// A check to see if finish(::) was ever called to retreive data object
|
||||
private var finished = false
|
||||
/// A check to see if the buffer should serialize Default values
|
||||
@@ -107,7 +107,7 @@ public struct FlatBufferBuilder {
|
||||
/// - Parameters:
|
||||
/// - table: offset for the table
|
||||
/// - fields: Array of all the important fields to be serialized
|
||||
mutating public func require(table: Offset<UOffset>, fields: [Int32]) {
|
||||
mutating public func require(table: Offset, fields: [Int32]) {
|
||||
for field in fields {
|
||||
let start = _bb.capacity &- Int(table.o)
|
||||
let startTable = start &- Int(_bb.read(def: Int32.self, position: start))
|
||||
@@ -121,7 +121,7 @@ public struct FlatBufferBuilder {
|
||||
/// - offset: Offset of the table
|
||||
/// - fileId: Takes the fileId
|
||||
/// - prefix: if false it wont add the size of the buffer
|
||||
mutating public func finish<T>(offset: Offset<T>, fileId: String, addPrefix prefix: Bool = false) {
|
||||
mutating public func finish(offset: Offset, fileId: String, addPrefix prefix: Bool = false) {
|
||||
let size = MemoryLayout<UOffset>.size
|
||||
preAlign(len: size &+ (prefix ? size : 0) &+ FileIdLength, alignment: _minAlignment)
|
||||
assert(fileId.count == FileIdLength, "Flatbuffers requires file id to be 4")
|
||||
@@ -133,7 +133,7 @@ public struct FlatBufferBuilder {
|
||||
/// - Parameters:
|
||||
/// - offset: Offset of the table
|
||||
/// - prefix: if false it wont add the size of the buffer
|
||||
mutating public func finish<T>(offset: Offset<T>, addPrefix prefix: Bool = false) {
|
||||
mutating public func finish(offset: Offset, addPrefix prefix: Bool = false) {
|
||||
notNested()
|
||||
let size = MemoryLayout<UOffset>.size
|
||||
preAlign(len: size &+ (prefix ? size : 0), alignment: _minAlignment)
|
||||
@@ -296,7 +296,7 @@ public struct FlatBufferBuilder {
|
||||
///
|
||||
/// The current function will fatalError if startVector is called before serializing the vector
|
||||
/// - Parameter len: Length of the buffer
|
||||
mutating public func endVector(len: Int) -> Offset<UOffset> {
|
||||
mutating public func endVector(len: Int) -> Offset {
|
||||
assert(isNested, "Calling endVector without calling startVector")
|
||||
isNested = false
|
||||
return Offset(offset: push(element: Int32(len)))
|
||||
@@ -305,7 +305,7 @@ public struct FlatBufferBuilder {
|
||||
/// Creates a vector of type Scalar in the buffer
|
||||
/// - Parameter elements: elements to be written into the buffer
|
||||
/// - returns: Offset of the vector
|
||||
mutating public func createVector<T: Scalar>(_ elements: [T]) -> Offset<UOffset> {
|
||||
mutating public func createVector<T: Scalar>(_ elements: [T]) -> Offset {
|
||||
createVector(elements, size: elements.count)
|
||||
}
|
||||
|
||||
@@ -313,7 +313,7 @@ public struct FlatBufferBuilder {
|
||||
/// - Parameter elements: Elements to be written into the buffer
|
||||
/// - Parameter size: Count of elements
|
||||
/// - returns: Offset of the vector
|
||||
mutating public func createVector<T: Scalar>(_ elements: [T], size: Int) -> Offset<UOffset> {
|
||||
mutating public func createVector<T: Scalar>(_ elements: [T], size: Int) -> Offset {
|
||||
let size = size
|
||||
startVector(size, elementSize: MemoryLayout<T>.size)
|
||||
_bb.push(elements: elements)
|
||||
@@ -323,7 +323,7 @@ public struct FlatBufferBuilder {
|
||||
/// Creates a vector of type Enums in the buffer
|
||||
/// - Parameter elements: elements to be written into the buffer
|
||||
/// - returns: Offset of the vector
|
||||
mutating public func createVector<T: Enum>(_ elements: [T]) -> Offset<UOffset> {
|
||||
mutating public func createVector<T: Enum>(_ elements: [T]) -> Offset {
|
||||
createVector(elements, size: elements.count)
|
||||
}
|
||||
|
||||
@@ -331,7 +331,7 @@ public struct FlatBufferBuilder {
|
||||
/// - Parameter elements: Elements to be written into the buffer
|
||||
/// - Parameter size: Count of elements
|
||||
/// - returns: Offset of the vector
|
||||
mutating public func createVector<T: Enum>(_ elements: [T], size: Int) -> Offset<UOffset> {
|
||||
mutating public func createVector<T: Enum>(_ elements: [T], size: Int) -> Offset {
|
||||
let size = size
|
||||
startVector(size, elementSize: T.byteSize)
|
||||
for e in elements.reversed() {
|
||||
@@ -343,7 +343,7 @@ public struct FlatBufferBuilder {
|
||||
/// Creates a vector of type Offsets in the buffer
|
||||
/// - Parameter offsets:Array of offsets of type T
|
||||
/// - returns: Offset of the vector
|
||||
mutating public func createVector<T>(ofOffsets offsets: [Offset<T>]) -> Offset<UOffset> {
|
||||
mutating public func createVector(ofOffsets offsets: [Offset]) -> Offset {
|
||||
createVector(ofOffsets: offsets, len: offsets.count)
|
||||
}
|
||||
|
||||
@@ -351,8 +351,8 @@ public struct FlatBufferBuilder {
|
||||
/// - Parameter elements: Array of offsets of type T
|
||||
/// - Parameter size: Count of elements
|
||||
/// - returns: Offset of the vector
|
||||
mutating public func createVector<T>(ofOffsets offsets: [Offset<T>], len: Int) -> Offset<UOffset> {
|
||||
startVector(len, elementSize: MemoryLayout<Offset<T>>.size)
|
||||
mutating public func createVector(ofOffsets offsets: [Offset], len: Int) -> Offset {
|
||||
startVector(len, elementSize: MemoryLayout<Offset>.size)
|
||||
for o in offsets.reversed() {
|
||||
push(element: o)
|
||||
}
|
||||
@@ -362,8 +362,8 @@ public struct FlatBufferBuilder {
|
||||
/// Creates a vector of Strings
|
||||
/// - Parameter str: a vector of strings that will be written into the buffer
|
||||
/// - returns: Offset of the vector
|
||||
mutating public func createVector(ofStrings str: [String]) -> Offset<UOffset> {
|
||||
var offsets: [Offset<String>] = []
|
||||
mutating public func createVector(ofStrings str: [String]) -> Offset {
|
||||
var offsets: [Offset] = []
|
||||
for s in str {
|
||||
offsets.append(create(string: s))
|
||||
}
|
||||
@@ -373,7 +373,7 @@ public struct FlatBufferBuilder {
|
||||
/// Creates a vector of `Native swift structs` which were padded to flatbuffers standards
|
||||
/// - Parameter structs: A vector of structs
|
||||
/// - Returns: offset of the vector
|
||||
mutating public func createVector<T: NativeStruct>(ofStructs structs: [T]) -> Offset<UOffset> {
|
||||
mutating public func createVector<T: NativeStruct>(ofStructs structs: [T]) -> Offset {
|
||||
startVector(structs.count * MemoryLayout<T>.size, elementSize: MemoryLayout<T>.alignment)
|
||||
for i in structs.reversed() {
|
||||
_ = create(struct: i)
|
||||
@@ -390,7 +390,7 @@ public struct FlatBufferBuilder {
|
||||
/// - Returns: offset of written struct
|
||||
@discardableResult
|
||||
mutating public func create<T: NativeStruct>(
|
||||
struct s: T, position: VOffset) -> Offset<UOffset>
|
||||
struct s: T, position: VOffset) -> Offset
|
||||
{
|
||||
let offset = create(struct: s)
|
||||
_vtableStorage.add(loc: FieldLoc(offset: _bb.size, position: VOffset(position)))
|
||||
@@ -403,7 +403,7 @@ public struct FlatBufferBuilder {
|
||||
/// - Returns: offset of written struct
|
||||
@discardableResult
|
||||
mutating public func create<T: NativeStruct>(
|
||||
struct s: T) -> Offset<UOffset>
|
||||
struct s: T) -> Offset
|
||||
{
|
||||
let size = MemoryLayout<T>.size
|
||||
preAlign(len: size, alignment: MemoryLayout<T>.alignment)
|
||||
@@ -416,7 +416,7 @@ public struct FlatBufferBuilder {
|
||||
/// Insets a string into the buffer using UTF8
|
||||
/// - Parameter str: String to be serialized
|
||||
/// - returns: The strings offset in the buffer
|
||||
mutating public func create(string str: String?) -> Offset<String> {
|
||||
mutating public func create(string str: String?) -> Offset {
|
||||
guard let str = str else { return Offset() }
|
||||
let len = str.utf8.count
|
||||
notNested()
|
||||
@@ -432,7 +432,7 @@ public struct FlatBufferBuilder {
|
||||
/// The function checks the stringOffsetmap if it's seen a similar string before
|
||||
/// - Parameter str: String to be serialized
|
||||
/// - returns: The strings offset in the buffer
|
||||
mutating public func createShared(string str: String?) -> Offset<String> {
|
||||
mutating public func createShared(string str: String?) -> Offset {
|
||||
guard let str = str else { return Offset() }
|
||||
if let offset = stringOffsetMap[str] {
|
||||
return offset
|
||||
@@ -448,7 +448,7 @@ public struct FlatBufferBuilder {
|
||||
/// - Parameters:
|
||||
/// - offset: Offset of another object to be written
|
||||
/// - position: The predefined position of the object
|
||||
mutating public func add<T>(offset: Offset<T>, at position: VOffset) {
|
||||
mutating public func add(offset: Offset, at position: VOffset) {
|
||||
if offset.isEmpty { return }
|
||||
add(element: refer(to: offset.o), def: 0, at: position)
|
||||
}
|
||||
@@ -457,7 +457,7 @@ public struct FlatBufferBuilder {
|
||||
/// - Parameter o: Offset
|
||||
/// - returns: Position of the offset
|
||||
@discardableResult
|
||||
mutating public func push<T>(element o: Offset<T>) -> UOffset {
|
||||
mutating public func push(element o: Offset) -> UOffset {
|
||||
push(element: refer(to: o.o))
|
||||
}
|
||||
|
||||
|
||||
@@ -20,15 +20,21 @@ import Foundation
|
||||
/// since now we will be serializing native structs into the buffer.
|
||||
public protocol NativeStruct {}
|
||||
|
||||
/// FlatbufferObject structures all the Flatbuffers objects
|
||||
public protocol FlatBufferObject {
|
||||
var __buffer: ByteBuffer! { get }
|
||||
/// FlatbuffersInitializable is a protocol that allows any object to be
|
||||
/// Initialized from a ByteBuffer
|
||||
public protocol FlatbuffersInitializable {
|
||||
init(_ bb: ByteBuffer, o: Int32)
|
||||
}
|
||||
|
||||
/// FlatbufferObject structures all the Flatbuffers objects
|
||||
public protocol FlatBufferObject: FlatbuffersInitializable {
|
||||
var __buffer: ByteBuffer! { get }
|
||||
}
|
||||
|
||||
public protocol ObjectAPIPacker {
|
||||
associatedtype T
|
||||
static func pack(_ builder: inout FlatBufferBuilder, obj: inout T) -> Offset<UOffset>
|
||||
static func pack(_ builder: inout FlatBufferBuilder, obj: inout T?) -> Offset
|
||||
static func pack(_ builder: inout FlatBufferBuilder, obj: inout T) -> Offset
|
||||
mutating func unpack() -> T
|
||||
}
|
||||
|
||||
|
||||
@@ -17,7 +17,7 @@
|
||||
import Foundation
|
||||
|
||||
/// Offset object for all the Objects that are written into the buffer
|
||||
public struct Offset<T> {
|
||||
public struct Offset {
|
||||
/// Offset of the object in the buffer
|
||||
public var o: UOffset
|
||||
/// Returns false if the offset is equal to zero
|
||||
|
||||
59
swift/Sources/FlatBuffers/String+extension.swift
Normal file
59
swift/Sources/FlatBuffers/String+extension.swift
Normal file
@@ -0,0 +1,59 @@
|
||||
/*
|
||||
* Copyright 2021 Google Inc. All rights reserved.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
import Foundation
|
||||
|
||||
extension String: FlatbuffersInitializable {
|
||||
|
||||
/// Initailizes a string from a Flatbuffers ByteBuffer
|
||||
/// - Parameters:
|
||||
/// - bb: ByteBuffer containing the readable string
|
||||
/// - o: Current position
|
||||
public init(_ bb: ByteBuffer, o: Int32) {
|
||||
let count = bb.read(def: Int32.self, position: Int(o))
|
||||
self = bb.readString(
|
||||
at: Int32(MemoryLayout<Int32>.size) + o,
|
||||
count: count) ?? ""
|
||||
}
|
||||
}
|
||||
|
||||
extension String: ObjectAPIPacker {
|
||||
|
||||
public static func pack(_ builder: inout FlatBufferBuilder, obj: inout String?) -> Offset {
|
||||
guard var obj = obj else { return Offset() }
|
||||
return pack(&builder, obj: &obj)
|
||||
}
|
||||
|
||||
public static func pack(_ builder: inout FlatBufferBuilder, obj: inout String) -> Offset {
|
||||
builder.create(string: obj)
|
||||
}
|
||||
|
||||
public mutating func unpack() -> String {
|
||||
self
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
extension String: NativeObject {
|
||||
|
||||
public func serialize<T: ObjectAPIPacker>(type: T.Type) -> ByteBuffer where T.T == Self {
|
||||
fatalError("serialize should never be called from string directly")
|
||||
}
|
||||
|
||||
public func serialize<T: ObjectAPIPacker>(builder: inout FlatBufferBuilder, type: T.Type) -> ByteBuffer where T.T == Self {
|
||||
fatalError("serialize should never be called from string directly")
|
||||
}
|
||||
}
|
||||
@@ -80,12 +80,12 @@ public struct Table {
|
||||
return r
|
||||
}
|
||||
|
||||
public func union<T: FlatBufferObject>(_ o: Int32) -> T {
|
||||
public func union<T: FlatbuffersInitializable>(_ o: Int32) -> T {
|
||||
let o = o + postion
|
||||
return directUnion(o)
|
||||
}
|
||||
|
||||
public func directUnion<T: FlatBufferObject>(_ o: Int32) -> T {
|
||||
public func directUnion<T: FlatbuffersInitializable>(_ o: Int32) -> T {
|
||||
T.init(bb, o: o + bb.read(def: Int32.self, position: Int(o)))
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user