diff --git a/languages.ts b/languages.ts
index 363de934c..69dd63602 100644
--- a/languages.ts
+++ b/languages.ts
@@ -40,6 +40,17 @@ const lispStyle: CommentStyle = {
},
}
+/**
+ * Filter a list of candidate definitions to select those likely to be valid
+ * cross-references for a definition in this file. Accept candidates located in
+ * files that are a suffix match (ignoring file extension) for some import of
+ * the current file.
+ *
+ * For imports we examine user `#include` and `#import` paths, as well as
+ * Objective C module `@import` package names. If no candidates match, fall
+ * back to the raw (unfiltered) results so that the user doesn't get an empty
+ * response unless there really is nothing.
+ */
const cppFilterDefinitions: HandlerArgs['filterDefinitions'] = ({
filePath,
fileContent,
@@ -48,17 +59,28 @@ const cppFilterDefinitions: HandlerArgs['filterDefinitions'] = ({
const imports = fileContent
.split(/\r?\n/)
.map(line => {
- const match = /^#include "(.*)"$/.exec(line)
- return match ? match[1] : undefined
+ // Rewrite `@import x.y.z;` as x/y/z to simulate path matching.
+ // In plain C and C++ files, expect this to be empty.
+ const matchImport = /^@import (\w+);$/.exec(line)
+ if (matchImport) {
+ return matchImport[1].replace(/\./g, '/')
+ }
+
+ // Capture paths from #include and #import directives.
+ // N.B. Only user paths ("") are captured, not system (<>) paths.
+ return /^#(include|import) "(.*)"$/.exec(line)?.[2]
})
.filter((x): x is string => Boolean(x))
+ // Select results whose file path shares a suffix with some import.
+ // N.B. Paths are compared without file extensions.
const filteredResults = results.filter(result => {
- return imports.some(i =>
- path
- .join(path.parse(result.file).dir, path.parse(result.file).name)
- .endsWith(path.join(path.parse(i).dir, path.parse(i).name))
- )
+ const resultParsed = path.parse(result.file)
+ const candidate = path.join(resultParsed.dir, resultParsed.name)
+ return imports.some(i => {
+ const iParsed = path.parse(i)
+ return candidate.endsWith(path.join(iParsed.dir, iParsed.name))
+ })
})
return filteredResults.length === 0 ? results : filteredResults
@@ -258,6 +280,7 @@ export const languageSpecs: LanguageSpec[] = [
'h',
'hpp',
/* Arduino */ 'ino',
+ /* Objective C */ 'm',
],
commentStyle: cStyle,
filterDefinitions: cppFilterDefinitions,
diff --git a/package.json b/package.json
index 3796b8cb8..45b8c792e 100644
--- a/package.json
+++ b/package.json
@@ -2,11 +2,11 @@
"license": "MIT",
"scripts": {
"prettier": "prettier '{package,template,generator}/**/*.{js?(on),ts,yml,md}' languages.ts --write --list-different",
- "prettier-check": "npm run prettier -- --write=false"
+ "prettier-check": "yarn run prettier --write=false"
},
"devDependencies": {
"@sourcegraph/prettierrc": "^3.0.1",
- "prettier": "^1.18.2",
+ "prettier": "^1.19.1",
"typescript": "^3.7.2"
},
"dependencies": {
diff --git a/package/src/handler.ts b/package/src/handler.ts
index 80b077f77..a2831759b 100644
--- a/package/src/handler.ts
+++ b/package/src/handler.ts
@@ -206,15 +206,12 @@ export function wrapIndentationInCodeBlocks({
.map(line => ({ line, kind: kindOf(line) }))
function propagateProse(lines: typeof unknownLines): void {
- lines.reduce(
- (s, line) => {
- if (line.kind === undefined && s === 'prose') {
- line.kind = 'prose'
- }
- return line.kind
- },
- 'prose' as LineKind | undefined
- )
+ lines.reduce((s, line) => {
+ if (line.kind === undefined && s === 'prose') {
+ line.kind = 'prose'
+ }
+ return line.kind
+ }, 'prose' as LineKind | undefined)
}
propagateProse(unknownLines)
diff --git a/samples/objectivec.m b/samples/objectivec.m
new file mode 100644
index 000000000..b34bd5623
--- /dev/null
+++ b/samples/objectivec.m
@@ -0,0 +1,262 @@
+//////////////////////////////////////////////////////////////////////////////////
+//
+// B L I N K
+//
+// Copyright (C) 2016-2018 Blink Mobile Shell Project
+//
+// This file is part of Blink.
+//
+// Blink 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.
+//
+// Blink 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 Blink. If not, see .
+//
+// In addition, Blink is also subject to certain additional terms under
+// GNU GPL version 3 section 7.
+//
+// You should have received a copy of these additional terms immediately
+// following the terms and conditions of the GNU General Public License
+// which accompanied the Blink Source Code. If not, see
+// .
+//
+////////////////////////////////////////////////////////////////////////////////
+
+
+#import "GeoManager.h"
+#import
+#import
+#import
+#import
+
+NSString * BLGeoLockNotification = @"BLGeoLockNotification";
+
+@interface GeoManager()
+
+@end
+
+// https://gist.github.com/rsattar/b06060df7ea293b398d1
+NSDictionary *__locationToJson(CLLocation * location) {
+ NSMutableDictionary *gps = [NSMutableDictionary dictionary];
+
+ // Example:
+ /*
+ "{GPS}" = {
+ Altitude = "41.28771929824561";
+ AltitudeRef = 0;
+ DateStamp = "2014:07:21";
+ ImgDirection = "68.2140221402214";
+ ImgDirectionRef = T;
+ Latitude = "37.74252";
+ LatitudeRef = N;
+ Longitude = "122.42035";
+ LongitudeRef = W;
+ TimeStamp = "15:53:24";
+ };
+ */
+
+ // GPS tag version
+ // According to http://www.cipa.jp/std/documents/e/DC-008-2012_E.pdf,
+ // this value is 2.3.0.0
+ [gps setObject:@"2.3.0.0" forKey:(NSString *)kCGImagePropertyGPSVersion];
+
+ // Time and date must be provided as strings, not as an NSDate object
+ NSDateFormatter *formatter = [[NSDateFormatter alloc] init];
+ formatter.timeZone = [NSTimeZone timeZoneWithAbbreviation:@"UTC"];
+ formatter.dateFormat = @"HH:mm:ss.SSSSSS";
+ gps[(NSString *)kCGImagePropertyGPSTimeStamp] = [formatter stringFromDate:location.timestamp];
+ formatter.dateFormat = @"yyyy:MM:dd";
+ gps[(NSString *)kCGImagePropertyGPSDateStamp] = [formatter stringFromDate:location.timestamp];
+
+ // Latitude
+ CLLocationDegrees latitude = location.coordinate.latitude;
+ gps[(NSString *)kCGImagePropertyGPSLatitudeRef] = (latitude < 0) ? @"S" : @"N";
+ gps[(NSString *)kCGImagePropertyGPSLatitude] = @(fabs(latitude));
+
+ // Longitude
+ CLLocationDegrees longitude = location.coordinate.longitude;
+ gps[(NSString *)kCGImagePropertyGPSLongitudeRef] = (longitude < 0) ? @"W" : @"E";
+ gps[(NSString *)kCGImagePropertyGPSLongitude] = @(fabs(longitude));
+
+ // Degree of Precision
+ gps[(NSString *)kCGImagePropertyGPSDOP] = @(location.horizontalAccuracy);
+
+ // Altitude
+ CLLocationDistance altitude = location.altitude;
+ if (!isnan(altitude)) {
+ gps[(NSString *)kCGImagePropertyGPSAltitudeRef] = (altitude < 0) ? @(1) : @(0);
+ gps[(NSString *)kCGImagePropertyGPSAltitude] = @(fabs(altitude));
+ }
+
+ // Speed, must be converted from m/s to km/h
+ if (location.speed >= 0) {
+ gps[(NSString *)kCGImagePropertyGPSSpeedRef] = @"K";
+ gps[(NSString *)kCGImagePropertyGPSSpeed] = @(location.speed * (3600.0/1000.0));
+ }
+
+ // Direction of movement
+ if (location.course >= 0) {
+ gps[(NSString *)kCGImagePropertyGPSTrackRef] = @"T";
+ gps[(NSString *)kCGImagePropertyGPSTrack] = @(location.course);
+ }
+
+
+ return gps;
+}
+
+@implementation GeoManager {
+ CLLocationManager * _locManager;
+ NSMutableArray *_recentLocations;
+ NSNumber *_lockDistanceInMeters;
+ CLLocation *_lockCenter;
+}
+
+- (instancetype)init {
+ if (self = [super init]) {
+ _recentLocations = [[NSMutableArray alloc] init];
+ _locManager = [[CLLocationManager alloc] init];
+ _locManager.delegate = self;
+ _traking = NO;
+ }
+ return self;
+}
+
++ (GeoManager *)shared {
+ static GeoManager *manager = nil;
+ static dispatch_once_t onceToken;
+ dispatch_once(&onceToken, ^{
+ manager = [[self alloc] init];
+ });
+ return manager;
+}
+
+- (void)authorize {
+ [_locManager requestWhenInUseAuthorization];
+}
+
+- (void)start {
+ if (_traking) {
+ return;
+ }
+
+ _locManager.desiredAccuracy = 100000;
+ _locManager.allowsBackgroundLocationUpdates = YES;
+ _locManager.pausesLocationUpdatesAutomatically = NO;
+ [_locManager startUpdatingLocation];
+
+ _traking = YES;
+}
+
+- (void)lockInDistance:(NSNumber *)meters {
+ if (_traking) {
+ return;
+ }
+
+ _lockDistanceInMeters = meters;
+ _locManager.desiredAccuracy = kCLLocationAccuracyBestForNavigation;
+ _locManager.allowsBackgroundLocationUpdates = YES;
+ _locManager.pausesLocationUpdatesAutomatically = NO;
+ [_locManager startUpdatingLocation];
+
+ _traking = YES;
+}
+
+- (void)_postLockNotifications {
+ [[NSNotificationCenter defaultCenter] postNotificationName:BLGeoLockNotification object:nil];
+ UNUserNotificationCenter * center = [UNUserNotificationCenter currentNotificationCenter];
+ [center getNotificationSettingsWithCompletionHandler:^(UNNotificationSettings * _Nonnull settings) {
+ if (settings.authorizationStatus != UNAuthorizationStatusAuthorized) {
+ return;
+ }
+ if (settings.alertSetting != UNNotificationSettingEnabled) {
+ return;
+ }
+
+ UNMutableNotificationContent *content = [[UNMutableNotificationContent alloc] init];
+ content.title = @"Geo lock";
+ content.body = @"Your device get out of geo range lock.\nAll session are terminated.";
+ UNNotificationRequest *req = [UNNotificationRequest requestWithIdentifier:@"geo.lock" content:content trigger:nil];
+
+ [center addNotificationRequest:req withCompletionHandler:^(NSError * _Nullable error) {
+
+ }];
+ }];
+}
+
+- (void)locationManager:(CLLocationManager *)manager didUpdateLocations:(NSArray *)locations {
+ [_recentLocations addObjectsFromArray:locations];
+
+ if (_lockDistanceInMeters) {
+
+ if (_lockCenter) {
+ CLLocationDistance distance = [_lockCenter distanceFromLocation:[_recentLocations lastObject]];
+ if (distance > _lockDistanceInMeters.doubleValue) {
+ [self stop];
+ [self _postLockNotifications];
+ }
+ } else if (_recentLocations.count > 10) {
+ _lockCenter = [_recentLocations lastObject];
+ }
+ }
+
+ int maxHistory = 200;
+ if (_recentLocations.count > maxHistory) {
+ [_recentLocations removeObjectsInRange:NSMakeRange(0, _recentLocations.count - maxHistory)];
+ }
+}
+
+- (CLLocation * __nullable)lastLocation {
+ return [_recentLocations lastObject];
+}
+
+- (NSString *)currentJSON {
+ CLLocation * loc = [_recentLocations lastObject];
+ if (!loc) {
+ return @"{}";
+ }
+
+ NSData *data = [NSJSONSerialization dataWithJSONObject:__locationToJson(loc) options:NSJSONWritingPrettyPrinted error:nil];
+ return [[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding];
+}
+
+- (NSString *)lastJSONN:(int)n {
+ if (n <= 0) {
+ n = 1;
+ }
+ NSMutableArray *result = [[NSMutableArray alloc] init];
+ NSArray *locs = [_recentLocations copy];
+ if (locs.count == 0) {
+ return @"[]";
+ }
+ int i = (int)locs.count;
+ while (n > 0 && i > 0) {
+ i--;
+ n--;
+
+ CLLocation *loc = locs[i];
+ NSDictionary *json = __locationToJson(loc);
+ [result addObject: json];
+ }
+
+ NSData *data = [NSJSONSerialization dataWithJSONObject:result options:NSJSONWritingPrettyPrinted error:nil];
+ return [[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding];
+}
+
+- (void)stop {
+ if (_lockCenter) {
+ [_recentLocations removeAllObjects];
+ }
+ _lockDistanceInMeters = nil;
+ _lockCenter = nil;
+ [_locManager stopUpdatingLocation];
+ _traking = NO;
+}
+
+@end
diff --git a/template/src/extension.ts b/template/src/extension.ts
index 4c72151e5..17a042ac1 100644
--- a/template/src/extension.ts
+++ b/template/src/extension.ts
@@ -72,10 +72,9 @@ export function activate(ctx: sourcegraph.ExtensionContext = DUMMY_CTX): void {
// Unconditionally get search references and append them with
// precise results because LSIF data might be sparse. Remove any
// search-based result that occurs in a file with an LSIF result.
- const searchReferences = (await handler.references(
- doc,
- pos
- )).filter(fuzzyRef => !lsifFiles.has(file(fuzzyRef)))
+ const searchReferences = (
+ await handler.references(doc, pos)
+ ).filter(fuzzyRef => !lsifFiles.has(file(fuzzyRef)))
return [
...lsifValues,
diff --git a/template/yarn.lock b/template/yarn.lock
index d6ac1fa06..7843b7c67 100644
--- a/template/yarn.lock
+++ b/template/yarn.lock
@@ -761,10 +761,11 @@
integrity sha512-ONhaKPIufzzrlNbqtWFFd+jlnemX6lJAgq9ZeiZtS7I1PIf/la7CW4m83rTXRnVnsMbW2k56pGYu7AUFJD9Pow==
"@sourcegraph/basic-code-intel@../package":
- version "7.0.9"
+ version "10.0.0"
dependencies:
lodash "^4.17.11"
rxjs "^6.3.3"
+ semver "^6.3.0"
sourcegraph "^23.0.1"
vscode-languageserver-types "^3.14.0"
@@ -5405,7 +5406,7 @@ saxes@^3.1.9:
resolved "https://registry.yarnpkg.com/semver/-/semver-5.7.1.tgz#a954f931aeba508d307bbf069eff0c01c96116f7"
integrity sha512-sauaDf/PZdVgrLTNYHRtpXa1iRiKcaebiKQ1BJdpQlWH2lCvexQdX55snPFyK7QzpudqbCI0qXFfOasHdyNDGQ==
-semver@^6.0.0:
+semver@^6.0.0, semver@^6.3.0:
version "6.3.0"
resolved "https://registry.yarnpkg.com/semver/-/semver-6.3.0.tgz#ee0a64c8af5e8ceea67687b133761e1becbd1d3d"
integrity sha512-b39TBaTSfV6yBrapU89p5fKekE2m/NwnDocOVruQFS1/veMgdzuPcnOM34M6CwxW8jH/lxEa5rBoDeUwu5HHTw==
diff --git a/yarn.lock b/yarn.lock
index 7dfae045f..7fa29d3d1 100644
--- a/yarn.lock
+++ b/yarn.lock
@@ -12,10 +12,10 @@ path-browserify@^1.0.0:
resolved "https://registry.yarnpkg.com/path-browserify/-/path-browserify-1.0.0.tgz#40702a97af46ae00b0ea6fa8998c0b03c0af160d"
integrity sha512-Hkavx/nY4/plImrZPHRk2CL9vpOymZLgEbMNX1U0bjcBL7QN9wODxyx0yaMZURSQaUtSEvDrfAvxa9oPb0at9g==
-prettier@^1.18.2:
- version "1.18.2"
- resolved "https://registry.yarnpkg.com/prettier/-/prettier-1.18.2.tgz#6823e7c5900017b4bd3acf46fe9ac4b4d7bda9ea"
- integrity sha512-OeHeMc0JhFE9idD4ZdtNibzY0+TPHSpSSb9h8FqtP+YnoZZ1sl8Vc9b1sasjfymH3SonAF4QcA2+mzHPhMvIiw==
+prettier@^1.19.1:
+ version "1.19.1"
+ resolved "https://registry.yarnpkg.com/prettier/-/prettier-1.19.1.tgz#f7d7f5ff8a9cd872a7be4ca142095956a60797cb"
+ integrity sha512-s7PoyDv/II1ObgQunCbB9PdLmUcBZcnWOcxDh7O0N/UwDEsHyqkW+Qh28jW+mVuCdx7gLB0BotYI1Y6uI9iyew==
typescript@^3.7.2:
version "3.7.5"