-
Notifications
You must be signed in to change notification settings - Fork 432
/
Settings.scala
462 lines (427 loc) · 23.5 KB
/
Settings.scala
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
package li.cil.oc
import java.io._
import java.net.Inet4Address
import java.net.InetAddress
import java.util.UUID
import com.google.common.net.InetAddresses
import com.mojang.authlib.GameProfile
import com.typesafe.config._
import cpw.mods.fml.common.Loader
import cpw.mods.fml.common.versioning.DefaultArtifactVersion
import cpw.mods.fml.common.versioning.VersionRange
import li.cil.oc.api.component.TextBuffer.ColorDepth
import li.cil.oc.integration.Mods
import org.apache.commons.lang3.StringEscapeUtils
import scala.collection.convert.WrapAsScala._
import scala.io.Codec
import scala.io.Source
import scala.util.matching.Regex
class Settings(val config: Config) {
// ----------------------------------------------------------------------- //
// client
val screenTextFadeStartDistance = config.getDouble("client.screenTextFadeStartDistance")
val maxScreenTextRenderDistance = config.getDouble("client.maxScreenTextRenderDistance")
val textLinearFiltering = config.getBoolean("client.textLinearFiltering")
val textAntiAlias = config.getBoolean("client.textAntiAlias")
val robotLabels = config.getBoolean("client.robotLabels")
val soundVolume = config.getDouble("client.soundVolume").toFloat max 0 min 2
val fontCharScale = config.getDouble("client.fontCharScale") max 0.5 min 2
val hologramFadeStartDistance = config.getDouble("client.hologramFadeStartDistance") max 0
val hologramRenderDistance = config.getDouble("client.hologramRenderDistance") max 0
val hologramFlickerFrequency = config.getDouble("client.hologramFlickerFrequency") max 0
val hologramMaxScaleByTier = Array(config.getDoubleList("client.hologramMaxScale"): _*) match {
case Array(tier1, tier2) =>
Array((tier1: Double) max 1.0, (tier2: Double) max 1.0)
case _ =>
OpenComputers.log.warn("Bad number of hologram max scales, ignoring.")
Array(3.0, 4.0)
}
val hologramMaxTranslationByTier = Array(config.getDoubleList("client.hologramMaxTranslation"): _*) match {
case Array(tier1, tier2) =>
Array((tier1: Double) max 0.0, (tier2: Double) max 0.0)
case _ =>
OpenComputers.log.warn("Bad number of hologram max translations, ignoring.")
Array(0.25, 0.5)
}
val monochromeColor = Integer.decode(config.getString("client.monochromeColor"))
val fontRenderer = config.getString("client.fontRenderer")
// ----------------------------------------------------------------------- //
// computer
val threads = config.getInt("computer.threads") max 1
val timeout = config.getDouble("computer.timeout") max 0
val startupDelay = config.getDouble("computer.startupDelay") max 0.05
val ramSizes = Array(config.getIntList("computer.ramSizes"): _*) match {
case Array(tier1, tier2, tier3, tier4, tier5, tier6) =>
Array(tier1: Int, tier2: Int, tier3: Int, tier4: Int, tier5: Int, tier6: Int)
case _ =>
OpenComputers.log.warn("Bad number of RAM sizes, ignoring.")
Array(192, 256, 384, 512, 768, 1024)
}
val ramScaleFor64Bit = config.getDouble("computer.ramScaleFor64Bit") max 1
val cpuComponentSupport = Array(config.getIntList("computer.cpuComponentCount"): _*) match {
case Array(tier1, tier2, tier3) =>
Array(tier1: Int, tier2: Int, tier3: Int)
case _ =>
OpenComputers.log.warn("Bad number of CPU component counts, ignoring.")
Array(8, 12, 16)
}
val callBudgets = Array(config.getDoubleList("computer.callBudgets"): _*) match {
case Array(tier1, tier2, tier3) =>
Array(tier1: Double, tier2: Double, tier3: Double)
case _ =>
OpenComputers.log.warn("Bad number of CPU call budgets, ignoring.")
Array(0.5, 1.0, 1.5)
}
val canComputersBeOwned = config.getBoolean("computer.canComputersBeOwned")
val maxUsers = config.getInt("computer.maxUsers") max 0
val maxUsernameLength = config.getInt("computer.maxUsernameLength") max 0
val eraseTmpOnReboot = config.getBoolean("computer.eraseTmpOnReboot")
val executionDelay = config.getInt("computer.executionDelay") max 0
// computer.lua
val allowBytecode = config.getBoolean("computer.lua.allowBytecode")
// ----------------------------------------------------------------------- //
// robot
val allowActivateBlocks = config.getBoolean("robot.allowActivateBlocks")
val allowUseItemsWithDuration = config.getBoolean("robot.allowUseItemsWithDuration")
val canAttackPlayers = config.getBoolean("robot.canAttackPlayers")
val screwCobwebs = config.getBoolean("robot.notAfraidOfSpiders")
val swingRange = config.getDouble("robot.swingRange")
val useAndPlaceRange = config.getDouble("robot.useAndPlaceRange")
val itemDamageRate = config.getDouble("robot.itemDamageRate") max 0 min 1
val nameFormat = config.getString("robot.nameFormat")
// robot.xp
val baseXpToLevel = config.getDouble("robot.xp.baseValue") max 0
val constantXpGrowth = config.getDouble("robot.xp.constantGrowth") max 1
val exponentialXpGrowth = config.getDouble("robot.xp.exponentialGrowth") max 1
val robotActionXp = config.getDouble("robot.xp.actionXp") max 0
val robotExhaustionXpRate = config.getDouble("robot.xp.exhaustionXpRate") max 0
val robotOreXpRate = config.getDouble("robot.xp.oreXpRate") max 0
val bufferPerLevel = config.getDouble("robot.xp.bufferPerLevel") max 0
val toolEfficiencyPerLevel = config.getDouble("robot.xp.toolEfficiencyPerLevel") max 0
val harvestSpeedBoostPerLevel = config.getDouble("robot.xp.harvestSpeedBoostPerLevel") max 0
// ----------------------------------------------------------------------- //
// robot.delays
// Note: all delays are reduced by one tick to account for the tick they are
// performed in (since all actions are delegated to the server thread).
val turnDelay = (config.getDouble("robot.delays.turn") - 0.06) max 0.05
val moveDelay = (config.getDouble("robot.delays.move") - 0.06) max 0.05
val swingDelay = (config.getDouble("robot.delays.swing") - 0.06) max 0
val useDelay = (config.getDouble("robot.delays.use") - 0.06) max 0
val placeDelay = (config.getDouble("robot.delays.place") - 0.06) max 0
val dropDelay = (config.getDouble("robot.delays.drop") - 0.06) max 0
val suckDelay = (config.getDouble("robot.delays.suck") - 0.06) max 0
val harvestRatio = config.getDouble("robot.delays.harvestRatio") max 0
// ----------------------------------------------------------------------- //
// power
val pureIgnorePower = config.getBoolean("power.ignorePower")
lazy val ignorePower = pureIgnorePower || !Mods.isPowerProvidingModPresent
val tickFrequency = config.getDouble("power.tickFrequency") max 1
val chargeRateRobot = config.getDouble("power.chargerChargeRate")
val chargeRateTablet = config.getDouble("power.chargerChargeRateTablet")
val generatorEfficiency = config.getDouble("power.generatorEfficiency")
val solarGeneratorEfficiency = config.getDouble("power.solarGeneratorEfficiency")
val assemblerTickAmount = config.getDouble("power.assemblerTickAmount") max 1
val disassemblerTickAmount = config.getDouble("power.disassemblerTickAmount") max 1
val powerModBlacklist = config.getStringList("power.modBlacklist")
// power.buffer
val bufferCapacitor = config.getDouble("power.buffer.capacitor") max 0
val bufferCapacitorAdjacencyBonus = config.getDouble("power.buffer.capacitorAdjacencyBonus") max 0
val bufferComputer = config.getDouble("power.buffer.computer") max 0
val bufferRobot = config.getDouble("power.buffer.robot") max 0
val bufferConverter = config.getDouble("power.buffer.converter") max 0
val bufferDistributor = config.getDouble("power.buffer.distributor") max 0
val bufferCapacitorUpgrades = Array(config.getDoubleList("power.buffer.batteryUpgrades"): _*) match {
case Array(tier1, tier2, tier3) =>
Array(tier1: Double, tier2: Double, tier3: Double)
case _ =>
OpenComputers.log.warn("Bad number of battery upgrade buffer sizes, ignoring.")
Array(10000.0, 15000.0, 20000.0)
}
val bufferTablet = config.getDouble("power.buffer.tablet") max 0
val bufferAccessPoint = config.getDouble("power.buffer.accessPoint") max 0
// power.cost
val computerCost = config.getDouble("power.cost.computer") max 0
val robotCost = config.getDouble("power.cost.robot") max 0
val sleepCostFactor = config.getDouble("power.cost.sleepFactor") max 0
val screenCost = config.getDouble("power.cost.screen") max 0
val hologramCost = config.getDouble("power.cost.hologram") max 0
val hddReadCost = (config.getDouble("power.cost.hddRead") max 0) / 1024
val hddWriteCost = (config.getDouble("power.cost.hddWrite") max 0) / 1024
val gpuSetCost = (config.getDouble("power.cost.gpuSet") max 0) / Settings.basicScreenPixels
val gpuFillCost = (config.getDouble("power.cost.gpuFill") max 0) / Settings.basicScreenPixels
val gpuClearCost = (config.getDouble("power.cost.gpuClear") max 0) / Settings.basicScreenPixels
val gpuCopyCost = (config.getDouble("power.cost.gpuCopy") max 0) / Settings.basicScreenPixels
val robotTurnCost = config.getDouble("power.cost.robotTurn") max 0
val robotMoveCost = config.getDouble("power.cost.robotMove") max 0
val robotExhaustionCost = config.getDouble("power.cost.robotExhaustion") max 0
val wirelessCostPerRange = config.getDouble("power.cost.wirelessCostPerRange") max 0
val abstractBusPacketCost = config.getDouble("power.cost.abstractBusPacket") max 0
val geolyzerScanCost = config.getDouble("power.cost.geolyzerScan") max 0
val robotBaseCost = config.getDouble("power.cost.robotAssemblyBase") max 0
val robotComplexityCost = config.getDouble("power.cost.robotAssemblyComplexity") max 0
val tabletBaseCost = config.getDouble("power.cost.tabletAssemblyBase") max 0
val tabletComplexityCost = config.getDouble("power.cost.tabletAssemblyComplexity") max 0
val disassemblerItemCost = config.getDouble("power.cost.disassemblerPerItem") max 0
val chunkloaderCost = config.getDouble("power.cost.chunkloaderCost") max 0
val pistonCost = config.getDouble("power.cost.pistonPush") max 0
// power.rate
val accessPointRate = config.getDouble("power.rate.accessPoint") max 0
val assemblerRate = config.getDouble("power.rate.assembler") max 0
val caseRate = (Array(config.getDoubleList("power.rate.case"): _*) match {
case Array(tier1, tier2, tier3) =>
Array(tier1: Double, tier2: Double, tier3: Double)
case _ =>
OpenComputers.log.warn("Bad number of computer case conversion rates, ignoring.")
Array(5.0, 10.0, 20.0)
}) ++ Array(9001.0)
// Creative case.
val chargerRate = config.getDouble("power.rate.charger") max 0
val disassemblerRate = config.getDouble("power.rate.disassembler") max 0
val powerConverterRate = config.getDouble("power.rate.powerConverter") max 0
val serverRackRate = config.getDouble("power.rate.serverRack") max 0
// power.value
private val valueAppliedEnergistics2 = config.getDouble("power.value.AppliedEnergistics2")
private val valueBuildCraft = config.getDouble("power.value.BuildCraft")
private val valueFactorization = config.getDouble("power.value.Factorization")
private val valueGalacticraft = config.getDouble("power.value.Galacticraft")
private val valueIndustrialCraft2 = config.getDouble("power.value.IndustrialCraft2")
private val valueMekanism = config.getDouble("power.value.Mekanism")
private val valueRedstoneFlux = config.getDouble("power.value.RedstoneFlux")
private val valueUniversalElectricity = config.getDouble("power.value.UniversalElectricity")
private val valueInternal = valueBuildCraft
val ratioAppliedEnergistics2 = valueAppliedEnergistics2 / valueInternal
val ratioBuildCraft = valueBuildCraft / valueInternal
val ratioFactorization = valueFactorization / valueInternal
val ratioGalacticraft = valueGalacticraft / valueInternal
val ratioIndustrialCraft2 = valueIndustrialCraft2 / valueInternal
val ratioMekanism = valueMekanism / valueInternal
val ratioRedstoneFlux = valueRedstoneFlux / valueInternal
val ratioUniversalElectricity = valueUniversalElectricity / valueInternal
// ----------------------------------------------------------------------- //
// filesystem
val fileCost = config.getInt("filesystem.fileCost") max 0
val bufferChanges = config.getBoolean("filesystem.bufferChanges")
val hddSizes = Array(config.getIntList("filesystem.hddSizes"): _*) match {
case Array(tier1, tier2, tier3) =>
Array(tier1: Int, tier2: Int, tier3: Int)
case _ =>
OpenComputers.log.warn("Bad number of HDD sizes, ignoring.")
Array(1024, 2048, 4096)
}
val floppySize = config.getInt("filesystem.floppySize") max 0
val tmpSize = config.getInt("filesystem.tmpSize") max 0
val maxHandles = config.getInt("filesystem.maxHandles") max 0
val maxReadBuffer = config.getInt("filesystem.maxReadBuffer") max 0
// ----------------------------------------------------------------------- //
// internet
val httpEnabled = config.getBoolean("internet.enableHttp")
val tcpEnabled = config.getBoolean("internet.enableTcp")
val httpHostBlacklist = Array(config.getStringList("internet.blacklist").map(new Settings.AddressValidator(_)): _*)
val httpHostWhitelist = Array(config.getStringList("internet.whitelist").map(new Settings.AddressValidator(_)): _*)
val httpTimeout = (config.getInt("internet.requestTimeout") max 0) * 1000
val httpMaxDownloadSize = config.getInt("internet.requestMaxDownloadSize") max 0
val maxConnections = config.getInt("internet.maxTcpConnections") max 0
val internetThreads = config.getInt("internet.threads") max 1
// ----------------------------------------------------------------------- //
// switch
val switchDefaultMaxQueueSize = config.getInt("switch.defaultMaxQueueSize") max 1
val switchQueueSizeUpgrade = config.getInt("switch.queueSizeUpgrade") max 0
val switchDefaultRelayDelay = config.getInt("switch.defaultRelayDelay") max 1
val switchRelayDelayUpgrade = config.getInt("switch.relayDelayUpgrade") max 0
val switchDefaultRelayAmount = config.getInt("switch.defaultRelayAmount") max 1
val switchRelayAmountUpgrade = config.getInt("switch.relayAmountUpgrade") max 0
// ----------------------------------------------------------------------- //
// misc
val maxScreenWidth = config.getInt("misc.maxScreenWidth") max 1
val maxScreenHeight = config.getInt("misc.maxScreenHeight") max 1
val inputUsername = config.getBoolean("misc.inputUsername")
val maxClipboard = config.getInt("misc.maxClipboard") max 0
val maxNetworkPacketSize = config.getInt("misc.maxNetworkPacketSize") max 0
val maxOpenPorts = config.getInt("misc.maxOpenPorts") max 0
val maxWirelessRange = config.getDouble("misc.maxWirelessRange") max 0
val rTreeMaxEntries = 10
val terminalsPerTier = Array(config.getIntList("misc.terminalsPerTier"): _*) match {
case Array(tier1, tier2, tier3) =>
Array(math.max(tier1, 1), math.max(tier2, 1), math.max(tier3, 1))
case _ =>
OpenComputers.log.warn("Bad number of Remote Terminal counts, ignoring.")
Array(2, 4, 8)
}
val updateCheck = config.getBoolean("misc.updateCheck")
val lootProbability = config.getInt("misc.lootProbability")
val geolyzerRange = config.getInt("misc.geolyzerRange")
val geolyzerNoise = config.getDouble("misc.geolyzerNoise").toFloat max 0
val disassembleAllTheThings = config.getBoolean("misc.disassembleAllTheThings")
val disassemblerBreakChance = config.getDouble("misc.disassemblerBreakChance") max 0 min 1
val hideOwnPet = config.getBoolean("misc.hideOwnSpecial")
val allowItemStackInspection = config.getBoolean("misc.allowItemStackInspection")
val databaseEntriesPerTier = Array(9, 25, 81) // Not configurable because of GUI design.
// ----------------------------------------------------------------------- //
// integration
val modBlacklist = config.getStringList("integration.modBlacklist")
val peripheralBlacklist = config.getStringList("integration.peripheralBlacklist")
val fakePlayerUuid = config.getString("integration.fakePlayerUuid")
val fakePlayerName = config.getString("integration.fakePlayerName")
val fakePlayerProfile = new GameProfile(UUID.fromString(fakePlayerUuid), fakePlayerName)
// integration.vanilla
val enableInventoryDriver = config.getBoolean("integration.vanilla.enableInventoryDriver")
val enableTankDriver = config.getBoolean("integration.vanilla.enableTankDriver")
val allowItemStackNBTTags = config.getBoolean("integration.vanilla.allowItemStackNBTTags")
// ----------------------------------------------------------------------- //
// debug
val logLuaCallbackErrors = config.getBoolean("debug.logCallbackErrors")
val forceLuaJ = config.getBoolean("debug.forceLuaJ")
val allowUserdata = !config.getBoolean("debug.disableUserdata")
val allowPersistence = !config.getBoolean("debug.disablePersistence")
val limitMemory = !config.getBoolean("debug.disableMemoryLimit")
val forceCaseInsensitive = config.getBoolean("debug.forceCaseInsensitiveFS")
val logFullLibLoadErrors = config.getBoolean("debug.logFullNativeLibLoadErrors")
val forceNativeLib = config.getString("debug.forceNativeLibWithName")
val logOpenGLErrors = config.getBoolean("debug.logOpenGLErrors")
val logUnifontErrors = config.getBoolean("debug.logUnifontErrors")
val alwaysTryNative = config.getBoolean("debug.alwaysTryNative")
val debugPersistence = config.getBoolean("debug.verbosePersistenceErrors")
val nativeInTmpDir = config.getBoolean("debug.nativeInTmpDir")
val periodicallyForceLightUpdate = config.getBoolean("debug.periodicallyForceLightUpdate")
val insertIdsInConverters = config.getBoolean("debug.insertIdsInConverters")
val enableDebugCard = config.getBoolean("debug.enableDebugCard")
val registerLuaJArchitecture = config.getBoolean("debug.registerLuaJArchitecture")
}
object Settings {
val resourceDomain = "opencomputers"
val namespace = "oc:"
val savePath = "opencomputers/"
val scriptPath = "/assets/" + resourceDomain + "/lua/"
val screenResolutionsByTier = Array((50, 16), (80, 25), (160, 50))
val screenDepthsByTier = Array(ColorDepth.OneBit, ColorDepth.FourBit, ColorDepth.EightBit)
val deviceComplexityByTier = Array(12, 24, 32, 9001)
var rTreeDebugRenderer = false
var blockRenderId = -1
def basicScreenPixels = screenResolutionsByTier(0)._1 * screenResolutionsByTier(0)._2
private var settings: Settings = _
def get = settings
def load(file: File) = {
import scala.compat.Platform.EOL
// typesafe config's internal method for loading the reference.conf file
// seems to fail on some systems (as does their parseResource method), so
// we'll have to load the default config manually. This was reported on the
// Minecraft Forums, I could not reproduce the issue, but this version has
// reportedly fixed the problem.
val defaults = {
val in = classOf[Settings].getResourceAsStream("/application.conf")
val config = Source.fromInputStream(in)(Codec.UTF8).getLines().mkString("", EOL, EOL)
in.close()
ConfigFactory.parseString(config)
}
val config =
try {
val plain = Source.fromFile(file)(Codec.UTF8).getLines().mkString("", EOL, EOL)
val config = patchConfig(ConfigFactory.parseString(plain), defaults).withFallback(defaults)
settings = new Settings(config.getConfig("opencomputers"))
config
}
catch {
case e: Throwable =>
if (file.exists()) {
OpenComputers.log.warn("Failed loading config, using defaults.", e)
}
settings = new Settings(defaults.getConfig("opencomputers"))
defaults
}
try {
val renderSettings = ConfigRenderOptions.defaults.setJson(false).setOriginComments(false)
val nl = sys.props("line.separator")
val nle = StringEscapeUtils.escapeJava(nl)
val out = new PrintWriter(file)
out.write(config.root.render(renderSettings).lines.
// Indent two spaces instead of four.
map(line => """^(\s*)""".r.replaceAllIn(line, m => Regex.quoteReplacement(m.group(1).replace(" ", " ")))).
// Finalize the string.
filter(_ != "").mkString(nl).
// Newline after values.
replaceAll(s"((?:\\s*#.*$nle)(?:\\s*[^#\\s].*$nle)+)", "$1" + nl))
out.close()
}
catch {
case e: Throwable =>
OpenComputers.log.warn("Failed saving config.", e)
}
}
private val configPatches = Array(
// Upgrading to version 1.3, increased lower bounds for default RAM sizes
// and reworked the way black- and whitelisting works (IP based).
VersionRange.createFromVersionSpec("[0.0,1.3-alpha)") -> Array(
"computer.ramSizes",
"internet.blacklist",
"internet.whitelist"
),
// Upgrading to version 1.3.3, default power consumption of chunk loader
// reduced as discussed in #447.
VersionRange.createFromVersionSpec("[1.3.0,1.3.3)") -> Array(
"power.cost.chunkloaderCost"
),
// Upgrading to version 1.3.4+, computer.debug category was moved to top
// level debug category for more flexibility and some other settings merged
// into that new category.
VersionRange.createFromVersionSpec("1.3.3") -> Array(
"computer.debug",
"misc.alwaysTryNative",
"misc.verbosePersistenceErrors"
),
// Upgrading to version 1.3.5, added forgotten check for item stack,
// inspection, patch to true to avoid stuff suddenly breaking.
VersionRange.createFromVersionSpec("1.3.4") -> Array(
"misc.allowItemStackInspection"
)
)
// Checks the config version (i.e. the version of the mod the config was
// created by) against the current version to see if some hard changes
// were made. If so, the new default values are copied over.
private def patchConfig(config: Config, defaults: Config) = {
val mod = Loader.instance.activeModContainer
val prefix = "opencomputers."
val configVersion = new DefaultArtifactVersion(if (config.hasPath(prefix + "version")) config.getString(prefix + "version") else "0.0.0")
var patched = config
if (configVersion.compareTo(mod.getProcessedVersion) != 0) {
OpenComputers.log.info(s"Updating config from version '${configVersion.getVersionString}' to '${defaults.getString(prefix + "version")}'.")
patched = patched.withValue(prefix + "version", defaults.getValue(prefix + "version"))
for ((version, paths) <- configPatches if version.containsVersion(configVersion)) {
for (path <- paths) {
val fullPath = prefix + path
OpenComputers.log.info(s"Updating setting '$fullPath'. ")
if (defaults.hasPath(fullPath)) {
patched = patched.withValue(fullPath, defaults.getValue(fullPath))
}
else {
patched = patched.withoutPath(fullPath)
}
}
}
}
patched
}
val cidrPattern = """(\d{1,3}\.\d{1,3}\.\d{1,3}\.\d{1,3})(?:/(\d{1,2}))""".r
class AddressValidator(val value: String) {
val validator = try cidrPattern.findFirstIn(value) match {
case Some(cidrPattern(address, prefix)) =>
val addr = InetAddresses.coerceToInteger(InetAddresses.forString(address))
val mask = 0xFFFFFFFF << (32 - prefix.toInt)
val min = addr & mask
val max = min | ~mask
(inetAddress: InetAddress, host: String) => inetAddress match {
case v4: Inet4Address =>
val numeric = InetAddresses.coerceToInteger(v4)
min <= numeric && numeric <= max
case _ => true // Can't check IPv6 addresses so we pass them.
}
case _ =>
val address = InetAddress.getByName(value)
(inetAddress: InetAddress, host: String) => host == value || inetAddress == address
} catch {
case t: Throwable =>
OpenComputers.log.warn("Invalid entry in internet blacklist / whitelist: " + value, t)
(inetAddress: InetAddress, host: String) => true
}
def apply(inetAddress: InetAddress, host: String) = validator(inetAddress, host)
}
}